{"action":"created","issue":{"url":"https://api.github.com/repos/rails-api/active_model_serializers/issues/1883","repository_url":"https://api.github.com/repos/rails-api/active_model_serializers","labels_url":"https://api.github.com/repos/rails-api/active_model_serializers/issues/1883/labels{/name}","comments_url":"https://api.github.com/repos/rails-api/active_model_serializers/issues/1883/comments","events_url":"https://api.github.com/repos/rails-api/active_model_serializers/issues/1883/events","html_url":"https://github.com/rails-api/active_model_serializers/pull/1883","id":171470862,"number":1883,"title":"(WIP) Fix Serializer Lookup Chain for Namespaces","user":{"login":"thewatts","id":1141717,"avatar_url":"https://avatars.githubusercontent.com/u/1141717?v=3","gravatar_id":"","url":"https://api.github.com/users/thewatts","html_url":"https://github.com/thewatts","followers_url":"https://api.github.com/users/thewatts/followers","following_url":"https://api.github.com/users/thewatts/following{/other_user}","gists_url":"https://api.github.com/users/thewatts/gists{/gist_id}","starred_url":"https://api.github.com/users/thewatts/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thewatts/subscriptions","organizations_url":"https://api.github.com/users/thewatts/orgs","repos_url":"https://api.github.com/users/thewatts/repos","events_url":"https://api.github.com/users/thewatts/events{/privacy}","received_events_url":"https://api.github.com/users/thewatts/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":null,"assignees":[],"milestone":null,"comments":6,"created_at":"2016-08-16T17:21:51Z","updated_at":"2016-08-17T03:23:21Z","closed_at":null,"pull_request":{"url":"https://api.github.com/repos/rails-api/active_model_serializers/pulls/1883","html_url":"https://github.com/rails-api/active_model_serializers/pull/1883","diff_url":"https://github.com/rails-api/active_model_serializers/pull/1883.diff","patch_url":"https://github.com/rails-api/active_model_serializers/pull/1883.patch"},"body":"#### Purpose\r\n\r\nThis fixes dynamic lookup of namespaced serializers through relationships.\r\n\r\n#### Changes\r\n\r\nThis adjusts the internal API of the serializer method used for dynamic lookup by adding an additional constant string to the lookup chain used to find the related serializer. \r\n\r\n#### Caveats\r\n\r\nNo tests. I'm a testing guy - so, if someone can point me to where I should be testing this in the project, I will 100% write them.\r\n\r\nI'm guessing I'll need to start with `test/serializers/associations_test.rb`\r\n\r\nAlso - this is currently only working for a single nested resource, I'll adjust in short order to provide a dynamic amount of namespaced items.\r\n\r\n#### Related GitHub issues\r\nNot sure\r\n\r\n#### Additional helpful information\r\n\r\n-- The Problem:\r\n\r\nCurrently, when using a relationship from within a namespace, ex:\r\n\r\n```ruby\r\nmodule Api\r\n  class LessonSerializer < ApplicationSerializer\r\n    belongs_to :trait\r\n  end\r\nend\r\n```\r\n\r\nThe method to fetch a serializer builds a lookup chain of possible\r\nconstant names that gets looped over with `safe_constantize`. When using\r\nrelationships from within a namespace (like above), the lookup chain\r\nwould return this:\r\n\r\n```ruby\r\n[\r\n  \"Api::LessonSerializer::TraitSerializer\",\r\n  \"::TraitSerializer\",\r\n]\r\n```\r\n\r\nThis works fine the first time, as calling `.safe_constantize` on\r\n`\"Api::LessonSerializer::TraitSerializer\"` returns the correct constant\r\nin this case: `Api::TraitSerializer`.\r\n\r\nHowever, the _second_ time that the lookup has to happen (from a\r\ndifferent relationship), ex:\r\n\r\n```ruby\r\nmodule Api\r\n  class CourseSerializer < ApplicationSerializer\r\n    belongs_to :trait\r\n  end\r\nend\r\n```\r\n\r\nThe lookup chain returns a similar response:\r\n\r\n```ruby\r\n[\r\n  \"Api::CourseSerializer::TraitSerializer\",\r\n  \"::TraitSerializer\",\r\n]\r\n```\r\n\r\nBut at this point, calling `.safe_constantize` on\r\n`\"Api::CourseSerializer::TraitSerializer\"` returns `nil`.\r\n\r\nHere's an example from the Rails console:\r\n![safe_constantize example](https://thewatts.s3-us-west-1.amazonaws.com/screenshots/Screen-Shot-2016-08-16-10-45-05.png)\r\n\r\nIt looks like the main problem [lies in this issue here](https://github.com/rails/rails/issues/9286)\r\n(many thanks to @willcosgrove for finding it!)\r\n\r\nSo this means that calling `.safe_constantize` on the same name string\r\nreturns the constant the first time (based on\r\n`ActiveSupport::Dependencies`), but the _second_ time it gets called on\r\nthe same string it returns `nil`.\r\n\r\n![safe_constantize of the same string](https://thewatts.s3-us-west-1.amazonaws.com/screenshots/Screen-Shot-2016-08-16-10-53-15.png)\r\n\r\n-- The Fix:\r\n\r\nI get the namespace of the `name` of the parent serializer, and use that\r\nto also build and add a string to the lookup chain array.\r\n\r\nSo in our first example above, it adds: `\"Api::TraitSerializer\"` to the\r\nlookup chain, allowing the serializer to be found every time."},"comment":{"url":"https://api.github.com/repos/rails-api/active_model_serializers/issues/comments/240303652","html_url":"https://github.com/rails-api/active_model_serializers/pull/1883#issuecomment-240303652","issue_url":"https://api.github.com/repos/rails-api/active_model_serializers/issues/1883","id":240303652,"user":{"login":"thewatts","id":1141717,"avatar_url":"https://avatars.githubusercontent.com/u/1141717?v=3","gravatar_id":"","url":"https://api.github.com/users/thewatts","html_url":"https://github.com/thewatts","followers_url":"https://api.github.com/users/thewatts/followers","following_url":"https://api.github.com/users/thewatts/following{/other_user}","gists_url":"https://api.github.com/users/thewatts/gists{/gist_id}","starred_url":"https://api.github.com/users/thewatts/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thewatts/subscriptions","organizations_url":"https://api.github.com/users/thewatts/orgs","repos_url":"https://api.github.com/users/thewatts/repos","events_url":"https://api.github.com/users/thewatts/events{/privacy}","received_events_url":"https://api.github.com/users/thewatts/received_events","type":"User","site_admin":false},"created_at":"2016-08-17T03:23:21Z","updated_at":"2016-08-17T03:23:21Z","body":"@NullVoxPopuli for the lookup chain and versioning... would we try to specifically look for versioned namespaces?\r\n\r\nex: if `V2` exists, assume `V1` does as well? That could be tricky, since technically relationships could work both ways. `V1` of a Serializer starts using a `V2` of another."}}
{"actor":{"display_login":"thewatts"}}