{"action":"created","issue":{"url":"https://api.github.com/repos/w3c/webappsec/issues/221","labels_url":"https://api.github.com/repos/w3c/webappsec/issues/221/labels{/name}","comments_url":"https://api.github.com/repos/w3c/webappsec/issues/221/comments","events_url":"https://api.github.com/repos/w3c/webappsec/issues/221/events","html_url":"https://github.com/w3c/webappsec/issues/221","id":63130314,"number":221,"title":"CSP: Duplicate Directives should \"add\" instead of be ignored","user":{"login":"devd","id":136985,"avatar_url":"https://avatars.githubusercontent.com/u/136985?v=3","gravatar_id":"","url":"https://api.github.com/users/devd","html_url":"https://github.com/devd","followers_url":"https://api.github.com/users/devd/followers","following_url":"https://api.github.com/users/devd/following{/other_user}","gists_url":"https://api.github.com/users/devd/gists{/gist_id}","starred_url":"https://api.github.com/users/devd/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/devd/subscriptions","organizations_url":"https://api.github.com/users/devd/orgs","repos_url":"https://api.github.com/users/devd/repos","events_url":"https://api.github.com/users/devd/events{/privacy}","received_events_url":"https://api.github.com/users/devd/received_events","type":"User","site_admin":false},"labels":[{"url":"https://api.github.com/repos/w3c/webappsec/labels/CSP","name":"CSP","color":"207de5"}],"state":"open","locked":false,"assignee":null,"milestone":{"url":"https://api.github.com/repos/w3c/webappsec/milestones/1","html_url":"https://github.com/w3c/webappsec/milestones/CSP%203","labels_url":"https://api.github.com/repos/w3c/webappsec/milestones/1/labels","id":687744,"number":1,"title":"CSP 3","description":"","creator":{"login":"mikewest","id":1497,"avatar_url":"https://avatars.githubusercontent.com/u/1497?v=3","gravatar_id":"","url":"https://api.github.com/users/mikewest","html_url":"https://github.com/mikewest","followers_url":"https://api.github.com/users/mikewest/followers","following_url":"https://api.github.com/users/mikewest/following{/other_user}","gists_url":"https://api.github.com/users/mikewest/gists{/gist_id}","starred_url":"https://api.github.com/users/mikewest/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/mikewest/subscriptions","organizations_url":"https://api.github.com/users/mikewest/orgs","repos_url":"https://api.github.com/users/mikewest/repos","events_url":"https://api.github.com/users/mikewest/events{/privacy}","received_events_url":"https://api.github.com/users/mikewest/received_events","type":"User","site_admin":false},"open_issues":15,"closed_issues":2,"state":"open","created_at":"2014-06-11T07:23:42Z","updated_at":"2015-03-20T09:42:30Z","due_on":null,"closed_at":null},"comments":8,"created_at":"2015-03-20T01:13:44Z","updated_at":"2015-03-22T12:22:12Z","closed_at":null,"body":"the policy\r\n```\r\nobject-src 'none'; object-src 'self';\r\n```\r\nright now enforces \"'none'\".  Instead, I think it should append to the list of allowed object sources.\r\n\r\nCSP is already eminently unprogrammable based on control flow. Right now, the only way to set a CSP policy is to look at URL and set it. This reduces flexibility because later on, the code might realize \"I need to include an object\".\r\n\r\nBut now, it is impossible to take the existing CSP policy and append to it without writing a CSP policy parser.  AppServers only provide the API of setting a header and reading a header. The only alternative is to keep csp in a variable that is an array of hosts in a dictionary of directives and then modify that as you process and then at the end, serialize that and add that as a header. This is still very painful.\r\n\r\nIn general, the CSP will be written by the security / paranoid person in the team and not by all developers. After trying to use CSP at scale, I am convinced that it is more important to keep the CSP policy programmable instead of designing it to be a  super paranoid \"fail-closed\" model, which is doing more harm than good.\r\n\r\nIf you are worried about \"how can a team ensure an absolute minimum policy?\", we can do that by setting an additional header (since if there are 2 policies, both are enforced). Or, the CSP pinning proposal.\r\n\r\nFWIW, this is part of the reason why policy is \"https://* data:\" for most things other than scripts,objects because it is so painful to adapt the policy based on what the response is going to be. This also makes \"hash-src\" adoption difficult and we don't remove unsafe-inline/nonce even if the page doesn't need that."},"comment":{"url":"https://api.github.com/repos/w3c/webappsec/issues/comments/84597369","html_url":"https://github.com/w3c/webappsec/issues/221#issuecomment-84597369","issue_url":"https://api.github.com/repos/w3c/webappsec/issues/221","id":84597369,"user":{"login":"mikewest","id":1497,"avatar_url":"https://avatars.githubusercontent.com/u/1497?v=3","gravatar_id":"","url":"https://api.github.com/users/mikewest","html_url":"https://github.com/mikewest","followers_url":"https://api.github.com/users/mikewest/followers","following_url":"https://api.github.com/users/mikewest/following{/other_user}","gists_url":"https://api.github.com/users/mikewest/gists{/gist_id}","starred_url":"https://api.github.com/users/mikewest/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/mikewest/subscriptions","organizations_url":"https://api.github.com/users/mikewest/orgs","repos_url":"https://api.github.com/users/mikewest/repos","events_url":"https://api.github.com/users/mikewest/events{/privacy}","received_events_url":"https://api.github.com/users/mikewest/received_events","type":"User","site_admin":false},"created_at":"2015-03-22T12:22:12Z","updated_at":"2015-03-22T12:22:12Z","body":"Ok. I guess that's an argument for making it a standalone flag."}}