How do I "use" or import a local Rust file? [duplicate] - import

This question already has answers here:
How do I do a basic import/include of a function from one module to another in Rust 2015?
(3 answers)
Split a module across several files
(7 answers)
How can I include a module from another file from the same project?
(6 answers)
Closed 5 years ago.
How do I include a file with the full path my_project/src/include_me.rs in main.rs?
I've checked the dependencies guide, and all of them appear to be including a binary. I've also checked "The Book", but none of the examples there end in ".rs" either.
How do I make include_me.rs compile with the rest of the project?

There are basically two (main) ways in Rust to include code from somewhere else:
1. "Including" internal code
If your include_me.rs belongs to your project, you should move it to the same folder main.rs lies in:
└── src
├── include_me.rs
└── main.rs
Then you can write this in your main.rs:
mod include_me;
fn main() {
// Call a function defined in the other file (module)
include_me::some_function();
}
A mod declaration makes the Rust compiler look for the corresponding .rs files automatically!
So everything that belongs to your project, belongs in the same folder (or a subfolder thereof) as the folder where main.rs (or lib.rs) is lying. The files are then "included" via the module system. To read a good introduction into modules, please read the chapter on modules in the Rust book. You could also check out Rust by Example on that topic. The module system is pretty central and thus important to learning Rust.
2. "Including" external code
If your include_me.rs is something that doesn't belong to your actual project, but is rather a collection of useful things you are using in multiple projects, it should be seen as a library. To include code of such external libraries, you have to include it as an extern crate. And to make your life easier, you really want to use Cargo!
So let's prepare your include_me.rs as Cargo library project. You need the following file structure (which is automatically generated by cargo new my_library --lib):
. my_library
  ├── Cargo.toml
  └── src
  └── lib.rs
Now copy all the contents from include_me.rs into lib.rs (it is just convention to call the root file of a library project lib.rs). Let's say that the my_library folder's full path is ~/code/my_library.
Now let's prepare your main project's Cargo project. It has a similar file
structure (but a main.rs instead of lib.rs, because it's a executable-project, not a library-project):
. my_project
├── Cargo.toml
└── src
└── main.rs
To declare your dependency on my_library, you have to put this into your Cargo.toml:
[package]
name = "my_project"
version = "0.1.0"
authors = ["you"]
edition = "2018"
[dependencies]
my_library = { path = "~/code/my_library" }
You can also use relative paths ("../my_library"), but it only makes sense if you know that the two projects always stay where they are, relative to one another (like if they are both managed in the same repository).
Now you can, in your main.rs, write:
use my_library::some_function;
fn main() {
// Call a function defined in the other file (extern crate)
some_function();
}
If you want to upload any of those two projects, you have to interact with crates.io (or another crates registry, if your company has one), but this is another topic.
(Note: some time ago, it was necessary to write extern crate my_library; inside main.rs. This is not necessary anymore, but you might find old code with extern crate declarations.)
Any other ways?
Yes, but you shouldn't use those. There is the include!() macro which allows you to verbatim include other files, just like the #include from C-land. However, it is strongly discouraged to use this in situations where the module system would be able to solve your problem. include!() is only useful in very special situations, often linked to a more complex build system which generates code.

Related

How to remove error alert of header-only cmake project in vscode

When I develop a project that output is a shared library or executable, normally, I will use include_directories in the CMakeLists.txt of root directory. In such case, before I include a header within a translate unit, I can't use angle brackets to let headers include each other. I think it is because files in include_directories is not a part of project. I can fix this by using relative path, but when I have to import external project, this can not fixed easily.
Assume that I have a external project with a root CMakeLists.txt, which has this snippet
add_library(mylib INTERFACE)
target_include_directories(mylib INTERFACE .)
and the directory seems like this
└──external
├───mylib.hpp
└───CMakeLists.txt
I want to import this project, and I'm writing a header-only project. The file tree seems like this
├──external (above)
├──include
| ├──header.hpp
| └──CMakeLists.txt
└──CMakeLists.txt
The CMakeLists.txt in root directory is simply add_subdirectory(include), and here is the CMakeLists.txt in folder include
add_library(Header INTERFACE)
target_include_directories(Header INTERFACE .)
target_link_libraries(Header INTERFACE mylib)
Theoretically, I can now include mylib.hpp by #include <mylib.hpp>, but it is not the case. VSCode tells me it can't find this header file. As much as I know, the only way to solve this is add a translate unit and let the implementation code include the header.hpp. I have tested this several time. VSCode won't report this error as long as I add a cpp file and include that header, and once I remove the cpp file, the error appears again.
By the way, I have set "C_Cpp.default.configurationProvider": "ms-vscode.cmake-tools" in configuration file of vscode.
Please tell me how to fix this without a translate unit.

Correct way to infer relative path from project

Goal
I'd like to launch a CLI program closely related to my flutter project, i.e., the program is saved somewhere near the flutter project folder.
My end goal here, is so that I could release a separate problem outside of the flutter app bundle at a fixed location relative to the bundle, e.g., same parent folder, while flutter-built exe can still find the program automatically. The solution targets Windows/macOS.
Expectation
I expect that I could retrieve a standard project path, such as the path to main.dart, and go from there using relative paths. I was so spoiled by Python's __file__ and wish to see something similar. This is also fairly easy to do with Windows/macOS native API, like this
For example, say I created a project under this folder
/path/to/my/flutter_project
I expect to call a Dart API to get the path of main.dart like this
/path/to/my/flutter_project/lib/main.dart
Observation
According to this answer The closest thing I got with flutter, is
import 'dart:io' as io;
Uri filePath = io.Platform.script.resolve('.');
however, puts me to a prescribed location:
// macOS
~/Library/Containers/com.example.flutterRelpath/Data/
This is the package data folder instead of the project folder.
If I query the script itself using
io.Platform.script.path
I get
~/Library/Containers/com.example.flutterRelpath/Data/main.dart
which is not the physical location of the script.
Question
Does it mean that I would need an installer to install the CLI program there or prepare a UI for the user to specify the location before I could use it? This seems a lot of trouble.
There is no reason to obtain the path of the script, nor does that make sense to do in a compiled application as the source files are not directly used at runtime.
You can simply use a relative path to reference whatever file/executable you want.
final uri = Uri.file('relative/file/path');
This will give you a Uri to the path file in the file folder in the relative folder, which would be at the same level as your executable.
├── executable.exe
├── relative
│ └── file
│ └── path//The Uri will refer to HERE
In order for this to be a relative, the passed path must not start with a path separator. So it should not be:
final uri = Uri.file('/relative/file/path');
Have a look at the dcli package and the DartScript and DartProject classes. they have methods designed to provide exactly this type of path information.
E.g.
DartProject.self.pathToProjectRoot

Get Path to Subpackage in Python

I have a project that needs updating from python2 to python3. It currently uses pkg_resources, which has significant overhead (PyCon 2018 - Get Your Resources Faster with importlib.resources, by Barry Warsaw). It will be packaged into a zip file. The relevant portions of the package structure are:
+-- project/
|__+ __init__.py
|__+ main.py
|__resources/
| |__+ images/
| | |__ # program images
| |__+ logging/
| |__+ custom_logger.py
|__log/
|__+ project_log.log
Intent for Original Question
The intent for the original question was to ask "how does one get the absolute path to a subpackage from within another subpackage", but I did a poor job wording this. I thought since current working directory meant "path to where the cwd command is run from" that this could be used, but I later learned my understanding was incomplete. current working directory means (in layman's terms) "path to where the cwd command is run from on the commandline"). This is why I was having trouble. If I run my program from within the top-level package
C:\Users\usr\Destop\program>py main.py
and use pathlib.Path.cwd() in a .py file in any other subpackage (resources, logging, log), I will get the same answer:
C:\Users\usr\Destop\program
I learned this is proper behavior, but it means I cannot use relative paths to get from one subpackage to another (I need to use relative paths since I don't know where the end user will install this program on his/her machine).
Relevant 2nd Part to Question that was Not Well-Clarified
Since part of my need is to update to python3, both pkgutil and importlib.resources were investigated. Each of these require resources to be treated as packages, so to update to use either of them, I have to add __init__.py to the folders resources, logging, and log. Not a big deal thankfully as this isn't a large program.
Note, for backwards compatibility with minimal code reediting, a namespace renaming has been recommended and used by others (e.g. see (How to use importlib.resources.path(package, resource)?).:
try:
import importlib.resources as pkg_resources
except ImportError:
# Try backported to PY<37 `importlib_resources`.
import importlib_resources as pkg_resources
Neither pgkutil nor importlib.resources has a method that directly returns "this subpackage" (in the way that pathlib.Path.cwd() "directly returns" the cwd without any extra code), but I think importlib.resources has a method I can use that will require the least amount of code and still be understandable to readers. Please note the ask is to get the absolute path to "this subpackage" and nothing else. I do not want to have to use a different approach.
The methods I would use is
try:
import importlib.resources as pkg_resources
except ImportError:
# Try backported to PY<37 `importlib_resources`.
import importlib_resources as pkg_resources
with pkg_resources.path("logging", "__init__.py") as fl:
path = fl.parent.resolve()
Conclusion
Beyond this, I have no questions, because it will probably be judged as an "opinion" question. Please note the __file__ method is unacceptable as this does not work with zip packages (see PyCon 2018 - Get Your Resources Faster with importlib.resources, by Barry Warsaw). If there is anything incorrect in this approach or if it can be improved, I would like to know.
Any python file can access it's own location with file. Hence for example you could simply do
pathlib.Path(__file__).parent
to access the directory of the file that runs that code. This is independent from where you run the program from and/or where you install the program.

How to force right resource file to be used when calling from another module

Here is the scenario (newbie to spark scala so kindly bear with me)
1) I have module A and a config file under resources folder. Class C in module A reads this config to get information about the file paths
2) i am trying to call Class C (module A) from Module B (after importing the dependencies of Module A in module B)
3) Issue i am facing is Class C (module) code when invoked from Module B , is using the config from Module B instead of its own config in Module A
Note : code works perfectly when i call with in Module A but once i move this code to Module B its using the resources file in Module B instead of Module A resource file.
both the configs have same name.
From the discussion in regard to my original answer, which assumed Lightbend Config (commonly used in the Scala world), it's been discovered that some sort of config.xml is in src/main/resources for the respective modules. These files both end up on the classpath and each module attempts (by an at this point unspecified means) to load the config.xml resource.
The JVM when asked to load resources always loads the first which matches.
The easiest way in a small set of projects to address this collision is to not collide by giving the configs in each project different names.
An alternative which is viable in a larger set of projects is to use Lightbend Config which allows config file inclusion out of the box, as well as the ability to use environment variables to easily override configurations at runtime.
An elaborate strategy for a larger set of projects, depending on how compatible the XML schemas for the various module's config.xmls are (if they're being read using a schema) is to define a custom Maven build process which embeds config.xmls inside one another so that code in module A and module B can share a config.xml: A only cares about the portion of the config which came from A and B only cares about that from B. I'm not particularly familiar with how one would do this in Maven, but I can't think of a reason why it wouldn't be possible.

Golang Importing Issue

I'm trying to use import a package for internal use, but I have been having some issues.
My directory structure looks like this:
app/
model/
file1.go
file2.go
...
main.go
When I try to build the program, I get an error that looks something like this:
/usr/local/go/src/pkg/model (from $GOROOT)
I want to be able to call the model programs in any of my other programs in the app simply using:
import "app/model"
What are my options when it comes to doing this?
You import from GOPATH level .. all of your packages should live there.
For example, assuming your application is here:
$GOPATH/src/dtrinh100/app/
..and your package you wish to import is here:
$GOPATH/src/github.com/other/package
Your import would be:
import "github.com/other/package"
You should review the literature around what the GOPATH environment variable is all about. When beginning Go, it is important you understand its purpose and initially, you should place all of your projects/packages inside of the GOPATH.
When you import a custom package, Go looks for its definition in each workspace listed in the GOPATH environment variable. Your custom package should be defined in a src subdirectory.
If you keep your code in a source repository somewhere, then you should use the root of that source repository as your base path. For instance, if you have a GitHub account at github.com/user, that should be your base path.
Note that you don't need to publish your code to a remote repository before you can build it. It's just a good habit to organize your code as if you will publish it someday. In practice you can choose any arbitrary path name, as long as it is unique to the standard library and greater Go ecosystem.
You should use github.com/user as our base path. Create a directory inside your workspace in which to keep source code:
$ mkdir -p $GOPATH/src/github.com/user
You can look at How to Write Go Code for more details.