Is there an "internal" visibility level?

I'm developing a library in Rust and struggle to re-use my own code inside the crate because of private visibility.

Let say my crate name is my_crate and it contains two modules in src/ (defined as files): mod1 and mod2.

The file src/mod1.rs look like this:

pub struct Foo { }

impl Foo {
  fn private_foo(&self) { }
}

In this file I can use the private method. However, I cannot do that in src/mod2.rs:

use crate::mod1::*;

pub struct Bar { }

impl Bar {
  pub fn bar(&self) { 
    Foo().private_foo()
  }
}

I totally understand the reason behind this and I'm fine with this behavior. However, I'd like to declare and intermediate visibility level between public and private, something like an "internal" level which would allow some code to be private at the crate level instead of the module level. Is there a way to achieve that?

In case I'm doing something wrong, here is my use case. I got a public struct with a private member:

pub struct Foo {
  value: String
}

which have a public constructor borrowing and cloning some data to populate the private member:

impl Foo {
  pub fn new(value: &str) -> Foo {
    Foo { value: String::from(value) }
  }
}

This constructor is fine but I'd like to avoid the clone internally in some situations. Unfortunately, the member wise constructor being private, I cannot use it outside of its module.

The best solutions I found are to change the public constructor to take a String as argument instead of a string slice reference, or to define a second public constructor taking a String as argument. The first solution is fine but loses some flexibility while the second clutter the API. Would you recommend me to use either of those or is there a better way?

You are looking for pub(crate).

4 Likes

Thanks for the quick answer, it's exactly what I'm looking for. For some reason I missed this point in the documentation.

Also keep in mind that sometimes sealed things may be better option.

These are public-in-the-name, but because they can not be named they can not be used directly outside of your crate.

Thanks for the tips.