42

Say I define my own type in a Rust library, like so:

struct Date {
    year: u16,
    month: u8,
    day: u8
}

impl Date {
    fn new(y: u16, m: u8, d: u8) -> Date {
        // Do some validation here first
        Date { year: y, month: m, day: d }
    }
}

Is there a way to require users to use the Date::new constructor? In other words, can I somehow prohibit users from creating their own Date struct using the following constructor:

let d = Date { 2017, 7, 10 };

I ask because it seems to be a detrimental flaw if you cannot force developers to run their arguments through a battery of validation before setting the members of a struct. (Although, maybe there is some other pattern that I should use in Rust, like validating data when they are used rather than when they are created; feel free to comment on that.)

1

1 Answer 1

41

TL;DR: The "default constructor" is disabled by default already.

The struct syntax is only available to those who have access to all the fields of the struct.

As a result, it is only accessible in the same module, as per privacy rules, unless all fields are marked pub in which case it is accessible wherever the struct is.

Note that the same is true of functions, since new is not marked pub here, it's inaccessible to any module other than the current one.

Sign up to request clarification or add additional context in comments.

5 Comments

Ah! Excellent. Thank you, sir!
@8bittree: No, it's an unless. Let me qualify it a bit more.
@8bittree: Great! Thanks for your feedback!
So, assuming the Date struct was public, how would I make sure user's were only able to make a Date using Date::new, but still be able to access the properties of Date? Would I have to make a 'throw away' private field in Date, i.e. struct Date { private_field_just_so_i_cant_be_instantiated: bool, ... }? (go easy on me, I'm just learning Rust :)
@jrahhali: You have a choice between "getters" to expose the properties, or a private field which in Rust you'd start with an underscore _ to avoid warnings of being unused. I personally would recommend getters, as private fields are better encapsulated, allowing to change the internal representation without breaking the interface.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.