Skip to content

Add authentication throughout sccache-dist, including simple token auth#274

Merged
luser merged 2 commits intomozilla:masterfrom
aidanhs:aphs-dist-sccache-simple-auth
Aug 30, 2018
Merged

Add authentication throughout sccache-dist, including simple token auth#274
luser merged 2 commits intomozilla:masterfrom
aidanhs:aphs-dist-sccache-simple-auth

Conversation

@aidanhs
Copy link
Contributor

@aidanhs aidanhs commented Aug 13, 2018

This adds

  • authenticated scheduler<->server communication in its (mostly) final form
  • the infrastructure for client<->scheduler communication, as well as a basic auth method (token)
  • job tokens to authenticate whatever you do with a job after the initial job creation

Should be reviewed after #271

@aidanhs aidanhs force-pushed the aphs-dist-sccache-simple-auth branch from 9f2bd00 to 30e5be5 Compare August 16, 2018 20:16
// TODO: for some reason these don't get called out in specific help if they're omitted
.requires_if("overlay", "overlay-build-dir")
.requires_if("overlay", "overlay-bwrap-path")
.subcommand(SubCommand::with_name("auth")
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

New utility subcommand of sccache-dist

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note also that scheduler and server move to being configured solely by config files which I found to be more future-proof.

@aidanhs
Copy link
Contributor Author

aidanhs commented Aug 16, 2018

Rebased and added the docs for this initial authentication (unfortunately it depends on the Windows PR due to some slight overlaps). You can just review the last commit though, as it's all in there.

@luser
Copy link
Contributor

luser commented Aug 24, 2018

Does this need to be rebased atop the landing of #271 ?

Cargo.toml Outdated
hyper-tls = { version = "0.1", optional = true }
jobserver = "0.1"
jsonwebtoken = { version = "4.0", optional = true }
jsonwebtoken = "4.0.1"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This could remain optional and be listed under dist and dist-server, right?

@@ -0,0 +1,212 @@
= Distributed sccache
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The formatting seems a bit off on this. Markdown uses # for headers, not =.

automatically package the compiler in use, while Windows and OSX users will
need to specify a toolchain for cross-compilation ahead of time.

== Communication
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this section would be better at the end or in a separate file, as it's less useful to end users than everything else in here.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This doc is actually intended as a deep dive into the technical details of how distributed sccache works and the implications of certain decisions. The user-facing doc will come later, as part of describing how to install and set it up.

follows:

```
server_auth = { type = "jwt_hs256", secret_key = "YOUR_KEY_HERE" }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be great to have examples of full config files for each of the scheduler, client, builder in the docs at some point.

src/dist/http.rs Outdated

split.next()
}
macro_rules! try_jwt_or_401 {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are these macros just so they can early-return?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yep


pub const HIDDEN_FILE_CONFIG_DATA_VAR: &str = "_SCCACHE_TEST_CONFIG";

pub const INSECURE_DIST_CLIENT_TOKEN: &str = "dangerously_insecure_client";
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This doesn't seem to match the value in the docs. Am I misinterpreting?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This token is the one used when you specify DANGEROUSLY_INSECURE mode in your config file. The exact value is left undocumented in the readme as there's no reason to know it (it's enough for it to be harcoded).

Ok(0)
},
Command::Auth(AuthSubcommand::JwtHS256ServerToken { secret_key, server_id }) => {
let header = jwt::Header::new(jwt::Algorithm::HS256);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This feels like it could all get split out into a separate function.

},

Command::Scheduler(scheduler_config::Config { client_auth, server_auth }) => {
let check_client_auth: Box<Fn(&str) -> bool + Send + Sync> = match client_auth {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oops, I meant to put that comment here.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The separate function bit? I'm not clear - what do you think could go in that function?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was just thinking that extracting the meat of this match arm into a separate function would make this function smaller and easier to follow. It's not a huge concern.

let server_id = ServerId(public_addr);
let scheduler_auth = match scheduler_auth {
server_config::SchedulerAuth::Insecure => {
create_server_token(server_id, &INSECURE_DIST_SERVER_TOKEN)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to log a warning on server startup for the insecure case.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point.

(job_id, server_id, auth)
} else {
let msg = format!("Insufficient capacity: {} available servers", servers.len());
let msg = format!("Insufficient capacity across {} available servers", num_servers);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems unfortunate. If a client tries to request a job that we don't have capacity for, it fails? I'd like to chat about this next time we talk.

Copy link
Contributor

@luser luser left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Overall this looks good! I'll let you rebase and merge this (if I didn't already grant you commit access to this repo I'll fix that as well).

@aidanhs aidanhs force-pushed the aphs-dist-sccache-simple-auth branch from 30e5be5 to f104074 Compare August 30, 2018 00:06
@aidanhs
Copy link
Contributor Author

aidanhs commented Aug 30, 2018

I've rebased and backported some conditional compilation cleanup (in light of the additional PRs coming through).

@aidanhs
Copy link
Contributor Author

aidanhs commented Aug 30, 2018

(I'm not going to go ahead and merge because I think it would be useful to get some eyes on it, since it involved a bit of shuffling)


impl Cfg {
pub fn scheduler_listen_addr() -> SocketAddr {
let ip_addr = "0.0.0.0".parse().unwrap();
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tend to prefer to write out the Ipv4Addr longhand, like:

let addr = SocketAddrV4::new(Ipv4Addr::new(127, 0, 0, 1), port);

@luser luser merged commit 105ab91 into mozilla:master Aug 30, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants