containers-roadmap icon indicating copy to clipboard operation
containers-roadmap copied to clipboard

[Fargate] [Network config in task definition]: Allow the task definition to contain the network configuration

Open iconara opened this issue 5 years ago • 7 comments

Tell us about your request Allow the task definition to contain network configuration such as subnets and security group.

Which service(s) is this request for? Fargate

Tell us about the problem you're trying to solve. What are you trying to do, and why is it hard? Currently the subnets and security groups to run a Fargate task in have to be specified when the task is run, and cannot be specified in the task definition.

This complicates things because it may be unnatural for the application starting a task to have to know these things. Its job may just be to start jobs, and it has no opinion about subnets and security groups. It might even be the case that the ops team would prefer it if the application couldn't choose these things, so that they could set up a task definition and have and application run tasks, and the ops team would know where these tasks were being run.

It would be great if Fargate could be used like Lamda: an application can invoke a function and it doesn't have to care about where the function runs (the function may even have an ENI and for all practical purposes do exactly the same thing as a Fargate task could do, run in the same VPC, or another VPC). With Fargate the caller needs to know the subnets where the task should run, and the security group, etc. – things that are unrelated to the work the caller wants to be performed.

Whether or not the network configuration should be in the task definition or not I don't know. I think it would make sense to have them in the cluster resource (because what's a cluster if not physical resource like a network?). The important thing is to minimize the amount of config that the runner of a task has to know to run the task.

Are you currently working around this issue? By having lots of copies of values like subnet ID, security group, all over the place.

Additional context This is related to #90

iconara avatar Jan 07 '19 15:01 iconara

@iconara I like the idea that Fargate could be used like Lambda!

For the specific problem you mentioned, I'd like to propose a workaround that you could use right now. When you set up the task definition, add tags to it that specify the extra configuration values needed to run it (subnets, security group, etc). Then in your code that starts the tasks, add a step to describe the task definition and get the tags, and use them for the API arguments.

Something like:

  1. Register the task definition:
aws ecs register-task-definition --cli-input-json file://my-task-def-input.json

(Its ARN will be returned in the output)

  1. Tag it with parameters needed at runtime
aws resourcegroupstaggingapi \
--resource-arn-list arn:aws:ecs:region:account-id:task-definition/my-task-def:1 
\ --tags subnet1=subnet-01ce11fbda8fafddd,subnet2=subnet-01244047ab9ea6ef1,assign_public_ip=DISABLED,cluster=my-cluster

(You can also add tags using the ECS APIs, but I prefer to use the separate tagging API). You could probably also use tags to store information for load balancers, placement strategies, service discovery, etc.

  1. Get the tags when you need to run the task def
aws ecs describe-task-definition --task-definition my-task-def:1  --include TAGS

What do you think of this idea?

PettitWesley avatar Jan 30 '19 00:01 PettitWesley

Thank you @PettitWesley for the suggestion, and that you like my proposal.

I don't think that workaround is better or worse than storing the same configuration in Parameter Store or a config file. What's good is that the IDs would be stored together with the TaskDefinition, which makes sense and in a way is what I'm asking for.

However, the RunTask caller still needs to be aware of the convention: to know that the IDs are stored in tags and the names of those tags. It would also not be less work – you don't have to read the TaskDefinition to do a RunTask call so it would be more or less exactly the same as using Parameter Store: one API call to something that contains configuration.

Ironically I think that a workaround closer to what I suggest is to create a Lambda function that does the RunTask call and reads the subnet and security group IDs from its environment variables.

On a side note it also feels like tagging in ECS/Fargate is not mature yet, and I would hesitate to build anything on top of it. You can't set tags from CloudFormation, and the way tags work with task definitions does not match the way task definitions are presented in the UI (it's closer in the API, though): The UI makes you think that revisions of a task definition have something to do with each other, so you expect that if you tag a task definition and create a new revision, the new revision has the same tags. In fact, revisions are unrelated and tags are not even copied when you create a new revision. That means that the solution you propose would also be brittle. If you use CloudFormation you would have to remember to manually add the tags again after every update, and the same if you use the UI. You must use the API directly, and you end up with your own custom tooling.

iconara avatar Jan 30 '19 07:01 iconara

Alternatively, the task could just default to the network configuration of its AWS::ECS::Service?

ronkorving avatar Aug 14 '19 06:08 ronkorving

I wonder why @ronkorving 's suggestion isn't already the default. If you don't specify an override at the time of starting a task, why would it error out, instead of use the services' default?

christopher-caldwell avatar Apr 14 '20 21:04 christopher-caldwell

Alternatively, the task could just default to the network configuration of its AWS::ECS::Service?

It wouldn't help if the task doesn't belong to a service.

alex35mil avatar Sep 04 '20 12:09 alex35mil

For me the simplest fix would be to have a networkConfiguration in the task definition, just as we already have a logConfiguration. If I need tasks with different network config, I just create different task definitions. At least for my use cases this would work very elegantly (especially with Terraform automation).

FWIW I've been banging my head against a wall to find a solution to this problem that doesn't require my task-triggering app to become infrastructure-aware. Would be awesome to see this resolved!

codelius avatar Jan 13 '21 16:01 codelius

+1: Just trying to bring this up again- it is a real pain to have to specify networking parameters when calling aws ecs run-task. In my opinion these should be defined in the task definition (at least as a default that could be optionally overridden).

md17482 avatar Aug 04 '22 14:08 md17482

In my list this is the biggest oversight of AWS API that I have encountered so far. To work around one needs to replicate network settings all over the place - bash scripts, makefiles, terraform, command line args etc. Not a nice experience indeed.

Really hope this issue gets some traction sooninsh.

vspinu avatar Aug 22 '22 10:08 vspinu