[mb-commits] branch, data-nes, updated. Edit note support

MusicBrainz Git Server <[email protected]> Fri, 18 Jan 2013 13:01:09 +0000
Newsgroups gmane.comp.audio.musicbrainz.cvs
Message-ID <E1TwBZF-0002BD-Pi@wiley>
The branch, data-nes has been updated
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=09ebef0867c96c787f10fce40f07dd2cdb4d09a3 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=dfc166add78ceae744371d17248c697b3e656f0b (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=524f96b02aa7c60c87dbf4f7ec31d59474e51950 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=4a3bcca371e40acdc9d7b7e42ee0c3fced3da57b (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=c9153d25cf38b65f96107e82da2b2e8b63cc2260 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=43ab95ad7dee3d6b6a73790b2e3ce378f2e8daa4 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=782d852cf868694897018618d8a0bc21bf0015a3 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=390bf9d8c36865f4b3a077606f1a6ae26a5aeda9 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=ab7a61997a56f575ee4e71654adbf75e88b6a935 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=caf9de70f841325776798e42fe427eb818a1aeb6 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=5c2a0683f00734e9bab07145be9837fc0b823ea9 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=880ac5612760bd18a52c763265143fd0fc6eaaaf (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=7cd2e4f98f2d39eb58d8863299b0dda2cf33a21b (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=7995b95a768488e984f6262d703c3aa5662cf284 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=e49cf6ca8b667a855c70154e41f68d49c3588227 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=1325f9847705187adb813bd3c07b15bf38deb6dd (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=9f8b507ccde409c49de32d419a78a024fcc8252f (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=307ae1782c63b423774864d8958250543eae7153 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=67e4160aebc2f03f6f9b89fa66dcd3a0239fde44 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=c27215820e3ef0ac600d2267539ea23de04b66fd (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=d303db03ba099e8d0d8e53765c3f5487fc68d98b (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=2fef60954ef27b4e1c1e3d2dba8402f4d978ae71 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=b771aee23fa66a37dca265f23b28097faeca1c56 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=eb08bdd9d0391058f9c9768bb64500d69ac7ee0e (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=3fa326a35da05c24985aeebd41f9d7b6a7e03e40 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=545d83e98188d9caaf2c2a19a8945bfcc76a9818 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=7f34d271fed459ea4b7da7cead5e2e0ee7cc4ee8 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=fb1ad49f5cddd906e7a6be72d2428298b922d271 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=539c7e504483397910080f9345b6303d7d21f9b4 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=38d50b727bca67910b113731a6bff534be256b81 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=09e04aff7d375c0d4eb94962012ee82452449d07 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=fca7018cca215b07f7d406aad0c040cc93bb99a3 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=1e2390975c307523b4cf76154728cb28b22110a6 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=611cc1d6778fbd402b760834445e36a8c47f696e (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=70c067ace6fe689c80248ecbedc8e29e8968d690 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=f8bafe63d85b2fe47d3c039586d9751a42eb4134 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=244b6589895bd37bc51d98f1d2e7380350e5816a (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=36b35231fd9902dfc11d86e4e85f29c18b38f4e1 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=fad66f00323fdf13a593c3a0a63f491aa6664cbd (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=0c46d04143f833c2543f09d271530f586f08161a (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=ddf62ca934f2916fa4eeaeac9e21bd3faf0f3d15 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=bc195f8980b361395a2632ef6cc77c593eaed690 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=9bb8c826cd2e6207aa170708bd7d8981841a938e (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=a8c7bb9774021f9812e856fcffd1c188a0a29bc2 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=d6d75499f5c4d3130e5dcad613125646b999a07d (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=a7fb2e7ae73b79d90d3a8cc075e506ad38792b57 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=a2dcbd32fb191638cd3ec7937afbc61ed25768f7 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=8bffcba5f8f3e5f39120ee4bb7c8ff62146ef804 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=d6936c0bc05e53587fc544dcdd8758eaa7e02a22 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=00d8d7d6d3ba6256d9ac057b2b9756166f3ddf33 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=9511434f8be3d563f824999872a3ceab4a1e66c6 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=e9e3c66ee4868a8863851bbbc1c2dc4327347d88 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=911264ab6646fb940a64cb687458cd88c53d80b5 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=041121a8112c734c71bc781bbb327d65ef3f4004 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=e6a0717337c0ace9ae85390a11c24b9b913aadb4 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=c1e8ded33b3861d13fa1defb95f6b59fa56cfb43 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=fe8f2a39159d24927da1aead28d3d88b3975c903 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=b0e91e2b4d4dd5e0aa51cbfd33d563f3df163ce3 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=4d46c76030cf48968970dd8acf1c2a1a5e239f28 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=4cd55df1a13d24553d3a309df2159ca94fc3883f (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=e3e7893631c1dc5adbb82e15abe30a969c087a07 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=8cca844437da56049acb9ba74bbb1ae8b3956a6b (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=273a40193dd1931c3697ab375bb8eadad0956e8c (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=57b24733ad8c09acd787d790d578d13f6c194088 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=f15d9d7855a1c72e773d868b59af5bc6ff9afaa6 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=e622f0cb411e4b0f26cda2232785e81926a70612 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=87782c1bb74e2191d2246b690b57eb7116a78f23 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=74d5095b28a6bef688218a8bf97bd249f36f1d25 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=aa9e0b923c6bc932b350f5eba946f86a7faaed3b (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=7d8fba4a49e610d1b921091f9385122cdb2c8187 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=69336dfff4cf6c55e77d71da69f3b41f6fb6fce4 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=0b2545647fd828b8b481b33d98796d969f583c09 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=55ba161a7b8548296dfa05876bb0285e7d8eb301 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=03046806a77180092f4cada41e60e6af0ce1ded7 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=7839a0eb19e4a98175c76a88774afab197731e21 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=d504762eafb9d3f47691dd85af6c64a062fd6670 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=5e1c19c76445fb769621b9192965b81b9fbb93cd (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=1d062f5859a24a41cc21877848edd64e853729a8 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=1d94f11c2d445ade701664945cc84d2065cce2d5 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=8a120396cc4ecd6d5f605d7e98ed815e8541e90f (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=6dfe1e4c67ed0833918d012343ca7a2a926836b1 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=144994457abfd3167b07e2b17d2b010f44fb2202 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=b9d1930b51fb4b8c7079b80eaeb32d40fe103a99 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=643f5f3350dd57aed9ec8f9d1636f664c4f65e1c (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=ace37903afc424b22bdc6ec6f528b84d20e725e9 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=83d9b1aec4128b7a7300aaa6de801724ecc4f007 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=f886b369f3179236a4b58f7be85ce41dbd687f07 (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=46ae32afdf4d50b1e56d156d0d01abb756aa641e (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=2239bfa441ab53566919a008fbb7acf410d6ecdc (commit)
  discards  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=7da9e13de2fab19882350610238708f9f2ffb3f6 (commit)
       via  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=82cd2edc485e7270f20283e7d471cf9e966657e7 (commit)
       via  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=4cc33e4b023b264a1dbee4d297e13fdf74de3348 (commit)
       via  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=55d91404e2afc9f326ec645bb613ed4ede19b156 (commit)
       via  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=1ad8a134940b0cc42ed82fb65f8bfde47e68d6bf (commit)
       via  http://git.musicbrainz.org/gitweb/?p=musicbrainz-server/core.git;a=commit;h=3614777669d554baf11d97869482b689b8ff5b71 (commit)

This update added new revisions after undoing existing revisions.  That is
to say, the old revision is not a strict subset of the new revision.  This
situation occurs when you --force push a change and generate a repository
containing something like this:

 * -- * -- B -- O -- O -- O (09ebef0867c96c787f10fce40f07dd2cdb4d09a3)
            \
             N -- N -- N (82cd2edc485e7270f20283e7d471cf9e966657e7)

When this happens we assume that you've already had alert emails for all
of the O revisions, and so we here report only the revisions in the N
branch from the common base, B.

Summary of changes:
 admin/replication/LoadReplicationChanges           |    6 -
 admin/replication/hooks/post-process.sample        |    8 -
 lib/DBDefs/Default.pm                              |   11 +-
 lib/MusicBrainz/Server.pm                          |  172 +++++++++-----------
 lib/MusicBrainz/Server/Connector.pm                |    3 +-
 lib/MusicBrainz/Server/Controller/WS/2/Release.pm  |    6 -
 lib/MusicBrainz/Server/Data/CoverArtArchive.pm     |   12 --
 lib/MusicBrainz/Server/Data/NES/Artist.pm          |   87 ----------
 lib/MusicBrainz/Server/Data/NES/CoreEntity.pm      |   30 ----
 lib/MusicBrainz/Server/Data/NES/Editor.pm          |   50 ------
 lib/MusicBrainz/Server/Data/NES/Entity.pm          |   83 ----------
 lib/MusicBrainz/Server/Data/NES/PartialDate.pm     |   33 ----
 lib/MusicBrainz/Server/Data/NES/Utils.pm           |   42 -----
 lib/MusicBrainz/Server/Data/URL.pm                 |    1 -
 lib/MusicBrainz/Server/Data/Work.pm                |    9 -
 lib/MusicBrainz/Server/Entity/NES/Edit.pm          |    6 -
 lib/MusicBrainz/Server/Entity/URL/TheSession.pm    |   36 ----
 lib/MusicBrainz/Server/Model/MB.pm                 |    6 +
 lib/MusicBrainz/Server/NES/Controller/Utils.pm     |   12 +--
 .../Server/WebService/Serializer/JSON/2/Release.pm |   14 +--
 lib/MusicBrainz/Server/WebService/XMLSerializer.pm |   16 --
 po/fixup/20130103-contexts.pl                      |   28 ----
 po/fixup/20130107-MBS-5651.py                      |   87 ----------
 po/mb_server.de.po                                 |    8 +-
 po/mb_server.el.po                                 |    6 +-
 po/mb_server.es.po                                 |    8 +-
 po/mb_server.et.po                                 |    8 +-
 po/mb_server.fi.po                                 |    8 +-
 po/mb_server.fr_FR.po                              |    6 +-
 po/mb_server.it.po                                 |    8 +-
 po/mb_server.nl.po                                 |    8 +-
 root/artist/recordings-list.tt                     |    2 +-
 root/cdstub/edit_form.tt                           |    2 +-
 root/cdstub/index.tt                               |    2 +-
 root/cdtoc/attach_artist_releases.tt               |    6 +-
 root/cdtoc/attach_confirm.tt                       |    4 +-
 root/cdtoc/attach_filter_artist.tt                 |    4 +-
 root/cdtoc/attach_filter_release.tt                |    6 +-
 root/components/common-macros.tt                   |    7 +-
 root/components/forms.tt                           |    6 +-
 root/components/wikipedia_extract.tt               |    2 +-
 root/edit/details/add_cover_art.tt                 |    2 +-
 root/edit/details/edit_cover_art.tt                |    3 +-
 root/edit/details/remove_cover_art.tt              |    2 +-
 root/edit/list.tt                                  |    4 +-
 root/layout/menu.tt                                |   12 +-
 root/main/401.tt                                   |    5 +-
 root/recording/add_isrc.tt                         |    4 +-
 root/recording/create.tt                           |    4 +-
 root/recording/layout.tt                           |    2 +-
 root/release/add_cover_art.tt                      |    4 +-
 root/release/cover_art.tt                          |    7 +-
 root/release/edit/information.tt                   |   11 +-
 root/release/edit/layout.tt                        |    4 +-
 root/release/edit/missing_entities.tt              |  166 +++++++++-----------
 root/release/edit/tracklist.tt                     |    4 +-
 root/release/reorder_cover_art.tt                  |    4 +-
 root/static/images/favicons/thesession-16.png      |  Bin 600 -> 0 bytes
 root/static/scripts/common/MB/utility.js           |    5 +
 .../static/scripts/edit/MB/Control/ArtistCredit.js |    8 +-
 root/static/scripts/edit/MB/Control/URLCleanup.js  |    4 +-
 .../release-editor/MB/Control/ReleaseEdits.js      |    2 +-
 .../release-editor/MB/Control/ReleaseRecordings.js |    2 +-
 .../release-editor/MB/Control/ReleaseTracklist.js  |    2 +-
 .../scripts/release-editor/MB/TrackParser.js       |   12 +-
 root/static/scripts/tests/Control/URLCleanup.js    |   25 ---
 root/static/styles/layout.css                      |    4 -
 root/user/ratings_summary.tt                       |    2 +-
 root/work/create.tt                                |    4 +-
 .../Server/Controller/WS/2/BrowseRelease.pm        |   48 ------
 .../Server/Controller/WS/2/JSON/BrowseReleases.pm  |   56 -------
 .../Server/Controller/WS/2/JSON/LookupRelease.pm   |   70 --------
 .../Server/Controller/WS/2/LookupDiscID.pm         |   18 --
 .../Server/Controller/WS/2/LookupNonCore.pm        |    6 -
 .../Server/Controller/WS/2/LookupRelationship.pm   |   12 --
 .../Server/Controller/WS/2/LookupRelease.pm        |   60 -------
 .../Server/Controller/WS/2/LookupTagsRatings.pm    |    6 -
 t/lib/t/MusicBrainz/Server/Data/NES/Artist.pm      |   64 --------
 t/lib/t/MusicBrainz/Server/Data/NES/Editor.pm      |   45 -----
 t/sql/statistics.sql                               |   10 +-
 t/sql/webservice.sql                               |    5 -
 81 files changed, 280 insertions(+), 1287 deletions(-)
 delete mode 100755 admin/replication/hooks/post-process.sample
 delete mode 100644 lib/MusicBrainz/Server/Data/NES/Artist.pm
 delete mode 100644 lib/MusicBrainz/Server/Data/NES/CoreEntity.pm
 delete mode 100644 lib/MusicBrainz/Server/Data/NES/Editor.pm
 delete mode 100644 lib/MusicBrainz/Server/Data/NES/Entity.pm
 delete mode 100644 lib/MusicBrainz/Server/Data/NES/PartialDate.pm
 delete mode 100644 lib/MusicBrainz/Server/Data/NES/Utils.pm
 delete mode 100644 lib/MusicBrainz/Server/Entity/NES/Edit.pm
 delete mode 100644 lib/MusicBrainz/Server/Entity/URL/TheSession.pm
 delete mode 100644 po/fixup/20130103-contexts.pl
 delete mode 100644 po/fixup/20130107-MBS-5651.py
 delete mode 100644 root/static/images/favicons/thesession-16.png
 delete mode 100644 t/lib/t/MusicBrainz/Server/Data/NES/Artist.pm
 delete mode 100644 t/lib/t/MusicBrainz/Server/Data/NES/Editor.pm

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 82cd2edc485e7270f20283e7d471cf9e966657e7
Author: Oliver Charles <[email protected]>
Date:   Fri Jan 18 12:55:43 2013 +0000

    Edit note support

diff --git a/lib/MusicBrainz/Server/Data/EditNote.pm b/lib/MusicBrainz/Server/Data/EditNote.pm
index 3ae226f..efe1da5 100644
--- a/lib/MusicBrainz/Server/Data/EditNote.pm
+++ b/lib/MusicBrainz/Server/Data/EditNote.pm
@@ -12,6 +12,8 @@ use MusicBrainz::Server::Data::Utils qw(
 
 extends 'MusicBrainz::Server::Data::Entity';
 
+with 'MusicBrainz::Server::Data::Role::NES';
+
 sub _table
 {
     return 'edit_note';
@@ -60,14 +62,13 @@ sub load_for_edits
 sub insert
 {
     my ($self, $edit_id, $note_hash) = @_;
-    my $mapping = $self->_column_mapping;
-    my %r = map {
-        my $key = $mapping->{$_} || $_;
-        $key => $note_hash->{$_};
-    } keys %$note_hash;
-    $r{edit} = $edit_id;
-    $self->sql->auto_commit;
-    $self->sql->insert_row('edit_note', \%r);
+    $self->request(
+        '/edit/add-note', {
+            edit => $edit_id,
+            editor => $note_hash->{editor_id},
+            text => $note_hash->{text}
+        }
+    );
 }
 
 sub add_note
@@ -75,33 +76,34 @@ sub add_note
     my ($self, $edit_id, $note_hash) = @_;
     $self->insert($edit_id, $note_hash);
 
-    my $email_data = MusicBrainz::Server::Email->new( c => $self->c );
-    my $edit = $self->c->model('Edit')->get_by_id($edit_id) or die "Edit $edit_id does not exist!";
-    $self->c->model('EditNote')->load_for_edits($edit);
-    $self->c->model('Vote')->load_for_edits($edit);
-    my $editors = $self->c->model('Editor')->get_by_ids($edit->editor_id,
-        $note_hash->{editor_id},
-        (map { $_->editor_id } @{ $edit->votes }),
-        (map { $_->editor_id } @{ $edit->edit_notes }));
-    $self->c->model('Editor')->load_preferences(values %$editors);
-
-    my @to_email = grep { $_ != $note_hash->{editor_id} }
-        map { $_->id } grep { $_->preferences->email_on_notes }
-        map { $editors->{$_->editor_id} }
-            @{ $edit->edit_notes },
-            @{ $edit->votes },
-            $edit;
-
-    my $from = $editors->{ $note_hash->{editor_id} };
-    for my $editor_id (uniq @to_email) {
-        my $editor = $editors->{ $editor_id };
-        $email_data->send_edit_note(
-            from_editor => $from,
-            editor => $editor,
-            note_text => $note_hash->{text},
-            edit_id => $edit_id,
-            own_edit => $edit->editor_id == $editor->id);
-    }
+    # NES
+    # my $email_data = MusicBrainz::Server::Email->new( c => $self->c );
+    # my $edit = $self->c->model('Edit')->get_by_id($edit_id) or die "Edit $edit_id does not exist!";
+    # $self->c->model('EditNote')->load_for_edits($edit);
+    # $self->c->model('Vote')->load_for_edits($edit);
+    # my $editors = $self->c->model('Editor')->get_by_ids($edit->editor_id,
+    #     $note_hash->{editor_id},
+    #     (map { $_->editor_id } @{ $edit->votes }),
+    #     (map { $_->editor_id } @{ $edit->edit_notes }));
+    # $self->c->model('Editor')->load_preferences(values %$editors);
+
+    # my @to_email = grep { $_ != $note_hash->{editor_id} }
+    #     map { $_->id } grep { $_->preferences->email_on_notes }
+    #     map { $editors->{$_->editor_id} }
+    #         @{ $edit->edit_notes },
+    #         @{ $edit->votes },
+    #         $edit;
+
+    # my $from = $editors->{ $note_hash->{editor_id} };
+    # for my $editor_id (uniq @to_email) {
+    #     my $editor = $editors->{ $editor_id };
+    #     $email_data->send_edit_note(
+    #         from_editor => $from,
+    #         editor => $editor,
+    #         note_text => $note_hash->{text},
+    #         edit_id => $edit_id,
+    #         own_edit => $edit->editor_id == $editor->id);
+    # }
 }
 
 no Moose;

commit 4cc33e4b023b264a1dbee4d297e13fdf74de3348
Author: Oliver Charles <[email protected]>
Date:   Fri Jan 18 12:54:37 2013 +0000

    Add support for creating and viewing aliases

diff --git a/lib/MusicBrainz/Server/Controller/Role/Alias.pm b/lib/MusicBrainz/Server/Controller/Role/Alias.pm
index 2df415f..d144d4a 100644
--- a/lib/MusicBrainz/Server/Controller/Role/Alias.pm
+++ b/lib/MusicBrainz/Server/Controller/Role/Alias.pm
@@ -9,6 +9,9 @@ use MusicBrainz::Server::Constants qw(
     $EDIT_WORK_ADD_ALIAS $EDIT_WORK_DELETE_ALIAS $EDIT_WORK_EDIT_ALIAS
 );
 
+use MusicBrainz::Server::Entity::Alias;
+use MusicBrainz::Server::NES::Controller::Utils qw( create_update );
+
 my %model_to_edit_type = (
     add => {
         Artist => $EDIT_ARTIST_ADD_ALIAS,
@@ -30,17 +33,27 @@ my %model_to_edit_type = (
 my %model_to_search_hint_type_id = (
     Artist => 3,
     Label => 2,
-    Work => 2
+    'NES::Work' => 2
 );
 
+sub alias_type_model {
+    my ($c, $parent) = @_;
+    my %type_model = (
+        'NES::Work' => 'Work'
+    );
+    return $c->model($type_model{$parent})->alias_type;
+}
+
 sub aliases : Chained('load') PathPart('aliases')
 {
     my ($self, $c) = @_;
 
     my $entity = $c->stash->{$self->{entity_name}};
-    my $m = $c->model($self->{model});
-    my $aliases = $m->alias->find_by_entity_id($entity->id);
-    $m->alias_type->load(@$aliases);
+    my $m = $self->{model};
+
+    my $aliases = $c->model($m)->get_aliases($entity);
+    alias_type_model($c, $m)->load(@$aliases);
+
     $c->stash(
         aliases => $aliases,
     );
@@ -57,25 +70,30 @@ sub alias : Chained('load') PathPart('alias') CaptureArgs(1)
 sub add_alias : Chained('load') PathPart('add-alias') RequireAuth Edit
 {
     my ($self, $c) = @_;
-    my $type = $self->{entity_name};
-    my $entity = $c->stash->{ $type };
-    my $alias_model = $c->model( $self->{model} )->alias;
-    $self->edit_action($c,
-        form => 'Alias',
-        form_args => {
-            parent_id => $entity->id,
-            alias_model => $alias_model,
-            search_hint_type_id => $model_to_search_hint_type_id{ $self->{model} }
-        },
-        type => $model_to_edit_type{add}->{ $self->{model} },
-        edit_args => {
-            entity => $entity
-        },
-        item => {
-            name => $entity->name,
-            id => $entity->id
+    my $entity = $c->stash->{entity};
+    my $model_name = $self->{model};
+
+    create_update(
+        $self, $c,
+        build_form => sub {
+            $c->form(
+                form => 'Alias',
+                search_hint_type_id => $model_to_search_hint_type_id{ $model_name },
+                type_model => alias_type_model($model_name),
+                init_object => { revision_id => $entity->revision_id }
+            );
         },
-        on_creation => sub { $self->_redir_to_aliases($c) }
+        build_tree => sub {
+            my ($values, $revision) = @_;
+
+            my $aliases = $c->model($model_name)->get_aliases($revision);
+            $self->{tree_entity}->new(
+                aliases => [
+                    @$aliases,
+                    MusicBrainz::Server::Entity::Alias->new($values)
+                ]
+            );
+        }
     );
 }
 
diff --git a/lib/MusicBrainz/Server/Controller/Work.pm b/lib/MusicBrainz/Server/Controller/Work.pm
index e50d49e..9a2a193 100644
--- a/lib/MusicBrainz/Server/Controller/Work.pm
+++ b/lib/MusicBrainz/Server/Controller/Work.pm
@@ -20,11 +20,11 @@ with 'MusicBrainz::Server::Controller::Role::Load' => {
     entity_name => 'work',
 };
 
+with 'MusicBrainz::Server::Controller::Role::Alias';
 with 'MusicBrainz::Server::Controller::Role::Details';
 with 'MusicBrainz::Server::Controller::Role::EditListing';
 with 'MusicBrainz::Server::Controller::Role::Rating';
 with 'MusicBrainz::Server::Controller::Role::Tag';
-# with 'MusicBrainz::Server::Controller::Role::Alias';
 # with 'MusicBrainz::Server::Controller::Role::Annotation';
 # with 'MusicBrainz::Server::Controller::Role::Relationship';
 # with 'MusicBrainz::Server::Controller::Role::Cleanup';
@@ -62,7 +62,7 @@ sub show : PathPart('') Chained('load')
 
 # NES - originally:
 # for my $action (qw( relationships aliases tags details )) {
-for my $action (qw( tags details )) {
+for my $action (qw( aliases tags details )) {
     after $action => sub {
         my ($self, $c) = @_;
         my $work = $c->stash->{work};
diff --git a/lib/MusicBrainz/Server/Data/NES/Work.pm b/lib/MusicBrainz/Server/Data/NES/Work.pm
index 3165b1b..4d3fc50 100644
--- a/lib/MusicBrainz/Server/Data/NES/Work.pm
+++ b/lib/MusicBrainz/Server/Data/NES/Work.pm
@@ -10,6 +10,8 @@ with 'MusicBrainz::Server::Data::Role::NES';
 sub create {
     my ($self, $edit, $editor, $tree) = @_;
 
+    $tree->aliases([]) unless $tree->aliases_set;
+
     my $response = $self->request('/work/create', {
         edit => $edit->id,
         editor => $editor->id,
@@ -25,7 +27,7 @@ sub update {
     die 'Need a base revision' unless $base_revision;
 
     my $final_tree = do {
-        if( $tree->work_set && $tree->iswcs_set ) {
+        if( $tree->work_set && $tree->aliases_set && $tree->iswcs_set ) {
             $tree
         }
         else {
@@ -34,6 +36,9 @@ sub update {
             $original_tree->work($tree->work)
                 if ($tree->work_set);
 
+            $original_tree->aliases($tree->aliases)
+                if ($tree->aliases_set);
+
             $original_tree->iswcs($tree->iswcs)
                 if ($tree->iswcs_set);
 
@@ -57,6 +62,7 @@ sub view_tree {
     return MusicBrainz::Server::Entity::Tree::Work->new(
         work => $revision,
         iswcs => $self->get_iswcs($revision),
+        aliases => $self->get_aliases($revision)
     );
 }
 
@@ -75,6 +81,18 @@ sub _work_tree {
         },
         iswcs => [
             map +{ iswc => $_ }, @{ $tree->iswcs }
+        ],
+        aliases => [
+            map +{
+                name => $_->name,
+                'sort-name' => $_->sort_name,
+                'begin-date' => partial_date_to_hash($_->begin_date),
+                'end-date' => partial_date_to_hash($_->end_date),
+                ended => $_->ended,
+                'primary-for-locale' => boolean($_->primary_for_locale),
+                type => $_->type_id,
+                locale => $_->locale
+            }, @{ $tree->aliases }
         ]
     );
 }
@@ -112,6 +130,27 @@ sub tags {
     $self->c->model('Work')->tags;
 }
 
+sub get_aliases {
+    my ($self, $work) = @_;
+    my $response = $self->request('/work/view-aliases', {
+        revision => $work->revision_id
+    });
+    return [
+        map {
+            MusicBrainz::Server::Entity::Alias->new(
+                name => $_->{name},
+                sort_name => $_->{'sort-name'},
+                locale => $_->{locale},
+                type_id => $_->{type},
+                begin_date => MusicBrainz::Server::Entity::PartialDate->new($_->{begin_date}),
+                end_date => MusicBrainz::Server::Entity::PartialDate->new($_->{end_date}),
+                ended => $_->{ended},
+                primary_for_locale => $_->{'primary-for-locale'}
+            )
+        } @$response
+    ]
+}
+
 sub get_iswcs {
     my ($self, $revision) = @_;
     warn "Unimplemented";
diff --git a/lib/MusicBrainz/Server/Entity/Alias.pm b/lib/MusicBrainz/Server/Entity/Alias.pm
index 36467df..1d29dec 100644
--- a/lib/MusicBrainz/Server/Entity/Alias.pm
+++ b/lib/MusicBrainz/Server/Entity/Alias.pm
@@ -18,12 +18,12 @@ has 'sort_name' => (
 
 has 'locale' => (
     is  => 'rw',
-    isa => 'Str',
+    isa => 'Maybe[Str]',
 );
 
 has 'type_id' => (
     is => 'rw',
-    isa => 'Int',
+    isa => 'Maybe[Int]',
 );
 
 has 'type' => (
diff --git a/lib/MusicBrainz/Server/Entity/Tree/Work.pm b/lib/MusicBrainz/Server/Entity/Tree/Work.pm
index 2e637b4..acf63f0 100644
--- a/lib/MusicBrainz/Server/Entity/Tree/Work.pm
+++ b/lib/MusicBrainz/Server/Entity/Tree/Work.pm
@@ -6,6 +6,11 @@ has work => (
     predicate => 'work_set',
 );
 
+has aliases => (
+    is => 'rw',
+    predicate => 'aliases_set',
+);
+
 has iswcs => (
     is => 'rw',
     predicate => 'iswcs_set',
diff --git a/lib/MusicBrainz/Server/Form/Alias.pm b/lib/MusicBrainz/Server/Form/Alias.pm
index c918b56..16ffbfc 100644
--- a/lib/MusicBrainz/Server/Form/Alias.pm
+++ b/lib/MusicBrainz/Server/Form/Alias.pm
@@ -43,14 +43,8 @@ has 'id' => (
     is  => 'rw',
 );
 
-has 'parent_id' => (
-    isa => 'Int',
-    is  => 'ro',
-    required => 1,
-);
-
-has 'alias_model' => (
-    isa => 'MusicBrainz::Server::Data::Alias',
+has 'type_model' => (
+    isa => 'MusicBrainz::Server::Data::AliasType',
     is  => 'ro',
     required => 1
 );
@@ -61,6 +55,10 @@ has search_hint_type_id => (
     required => 1
 );
 
+has_field revision_id => (
+    type => 'Integer',
+);
+
 sub edit_field_names {
     qw( name locale sort_name period.begin_date period.end_date
         type_id primary_for_locale )
@@ -94,7 +92,7 @@ sub options_locale {
 
 sub options_type_id {
     my $self = shift;
-    $self->_select_all($self->alias_model->parent->alias_type);
+    $self->_select_all($self->type_model);
 }
 
 sub validate_primary_for_locale {
@@ -115,13 +113,13 @@ after validate => sub {
         $sort_name_field->validate_field;
     }
 
-    if ($self->alias_model->exists({ name => $self->field('name')->value,
-                                     locale => $self->field('locale')->value,
-                                     type_id => $self->field('type_id')->value,
-                                     not_id => $self->init_object ? $self->init_object->{id} : undef,
-                                 })) {
-        $self->field('name')->add_error('This alias already exists');
-    }
+    # if ($self->alias_model->exists({ name => $self->field('name')->value,
+    #                                  locale => $self->field('locale')->value,
+    #                                  type_id => $self->field('type_id')->value,
+    #                                  not_id => $self->init_object ? $self->init_object->{id} : undef,
+    #                              })) {
+    #     $self->field('name')->add_error('This alias already exists');
+    # }
 };
 
 1;
diff --git a/root/alias/edit_form.tt b/root/alias/edit_form.tt
index b95c158..d27091d 100644
--- a/root/alias/edit_form.tt
+++ b/root/alias/edit_form.tt
@@ -20,6 +20,7 @@
         [% form_row_checkbox(r, 'primary_for_locale', l('This is the primary alias for this locale')) %]
       </span>
       [% form_row_select(r, 'type_id', l('Type:')) %]
+      [% r.hidden(form.field('revision_id')) %]
     </fieldset>
 
     <fieldset>

commit 55d91404e2afc9f326ec645bb613ed4ede19b156
Author: Oliver Charles <[email protected]>
Date:   Fri Jan 18 12:50:07 2013 +0000

    Enable tagging works

diff --git a/lib/MusicBrainz/Server/Controller/Role/Tag.pm b/lib/MusicBrainz/Server/Controller/Role/Tag.pm
index afeb136..4695ad1 100644
--- a/lib/MusicBrainz/Server/Controller/Role/Tag.pm
+++ b/lib/MusicBrainz/Server/Controller/Role/Tag.pm
@@ -14,9 +14,9 @@ after 'load' => sub
 
     my $entity = $c->stash->{$self->{entity_name}};
     my $tags_model = $c->model($self->{model})->tags;
-    my @tags = $tags_model->find_top_tags($entity->id, $TOP_TAGS_COUNT);
-    my $count = $tags_model->find_tag_count($entity->id);
-    my @user_tags = $tags_model->find_user_tags($c->user->id, $entity->id)
+    my @tags = $tags_model->find_top_tags($entity->gid, $TOP_TAGS_COUNT);
+    my $count = $tags_model->find_tag_count($entity->gid);
+    my @user_tags = $tags_model->find_user_tags($c->user->id, $entity->gid)
         if $c->user_exists;
 
     $c->stash(
@@ -71,11 +71,11 @@ sub tag_async : Chained('load') PathPart('ajax/tag') DenyWhenReadonly
 
     my $entity = $c->stash->{$self->{entity_name}};
     my $tags_model = $c->model($self->{model})->tags;
-    $tags_model->update($c->user->id, $entity->id, $c->req->params->{tags});
+    $tags_model->update($c->user->id, $entity->gid, $c->req->params->{tags});
 
-    my @user_tags = $tags_model->find_user_tags($c->user->id, $entity->id);
-    my @tags = $c->model($self->{model})->tags->find_top_tags($entity->id, $TOP_TAGS_COUNT);
-    my $count = $tags_model->find_tag_count($entity->id);
+    my @user_tags = $tags_model->find_user_tags($c->user->id, $entity->gid);
+    my @tags = $c->model($self->{model})->tags->find_top_tags($entity->gid, $TOP_TAGS_COUNT);
+    my $count = $tags_model->find_tag_count($entity->gid);
 
     my $response = {
         tags => [
diff --git a/lib/MusicBrainz/Server/Controller/Work.pm b/lib/MusicBrainz/Server/Controller/Work.pm
index 69b6933..e50d49e 100644
--- a/lib/MusicBrainz/Server/Controller/Work.pm
+++ b/lib/MusicBrainz/Server/Controller/Work.pm
@@ -23,7 +23,7 @@ with 'MusicBrainz::Server::Controller::Role::Load' => {
 with 'MusicBrainz::Server::Controller::Role::Details';
 with 'MusicBrainz::Server::Controller::Role::EditListing';
 with 'MusicBrainz::Server::Controller::Role::Rating';
-# with 'MusicBrainz::Server::Controller::Role::Tag';
+with 'MusicBrainz::Server::Controller::Role::Tag';
 # with 'MusicBrainz::Server::Controller::Role::Alias';
 # with 'MusicBrainz::Server::Controller::Role::Annotation';
 # with 'MusicBrainz::Server::Controller::Role::Relationship';
@@ -62,7 +62,7 @@ sub show : PathPart('') Chained('load')
 
 # NES - originally:
 # for my $action (qw( relationships aliases tags details )) {
-for my $action (qw( details )) {
+for my $action (qw( tags details )) {
     after $action => sub {
         my ($self, $c) = @_;
         my $work = $c->stash->{work};
diff --git a/lib/MusicBrainz/Server/Data/EntityTag.pm b/lib/MusicBrainz/Server/Data/EntityTag.pm
index d980035..d65d7e3 100644
--- a/lib/MusicBrainz/Server/Data/EntityTag.pm
+++ b/lib/MusicBrainz/Server/Data/EntityTag.pm
@@ -243,8 +243,9 @@ sub update
     @new_tags = $self->parse_tags($input);
 
     Sql::run_in_transaction(sub {
-        # Lock the entity being tagged to prevent concurrency issues
-        $self->parent->get_by_id_locked($entity_id);
+        # NES
+        # # Lock the entity being tagged to prevent concurrency issues
+        # $self->parent->get_by_id_locked($entity_id);
 
         # Load the existing raw tag ids for this entity
         my %old_tag_info;

commit 1ad8a134940b0cc42ed82fb65f8bfde47e68d6bf
Author: Oliver Charles <[email protected]>
Date:   Fri Jan 18 12:48:24 2013 +0000

    Enable rating works

diff --git a/lib/MusicBrainz/Server/Controller/Role/Rating.pm b/lib/MusicBrainz/Server/Controller/Role/Rating.pm
index a62cb0f..fa36f4b 100644
--- a/lib/MusicBrainz/Server/Controller/Role/Rating.pm
+++ b/lib/MusicBrainz/Server/Controller/Role/Rating.pm
@@ -8,7 +8,7 @@ sub ratings : Chained('load') PathPart('ratings')
     my ($self, $c) = @_;
 
     my $entity = $c->stash->{$self->{entity_name}};
-    my @ratings = $c->model($self->{model})->rating->find_by_entity_id($entity->id);
+    my @ratings = $c->model($self->{model})->rating->find_by_entity_id($entity->gid);
     $c->model('Editor')->load(@ratings);
     $c->model('Editor')->load_preferences(map { $_->editor } @ratings);
 
diff --git a/lib/MusicBrainz/Server/Controller/Work.pm b/lib/MusicBrainz/Server/Controller/Work.pm
index eba6f84..69b6933 100644
--- a/lib/MusicBrainz/Server/Controller/Work.pm
+++ b/lib/MusicBrainz/Server/Controller/Work.pm
@@ -22,7 +22,7 @@ with 'MusicBrainz::Server::Controller::Role::Load' => {
 
 with 'MusicBrainz::Server::Controller::Role::Details';
 with 'MusicBrainz::Server::Controller::Role::EditListing';
-# with 'MusicBrainz::Server::Controller::Role::Rating';
+with 'MusicBrainz::Server::Controller::Role::Rating';
 # with 'MusicBrainz::Server::Controller::Role::Tag';
 # with 'MusicBrainz::Server::Controller::Role::Alias';
 # with 'MusicBrainz::Server::Controller::Role::Annotation';
diff --git a/lib/MusicBrainz/Server/Data/Rating.pm b/lib/MusicBrainz/Server/Data/Rating.pm
index a35b41f..c53ce7b 100644
--- a/lib/MusicBrainz/Server/Data/Rating.pm
+++ b/lib/MusicBrainz/Server/Data/Rating.pm
@@ -82,7 +82,7 @@ sub load_user_ratings
 {
     my ($self, $user_id, @objs) = @_;
 
-    my %id_to_obj = map { $_->id => $_ } @objs;
+    my %id_to_obj = map { $_->gid => $_ } @objs;
     my @ids = keys %id_to_obj;
     return unless @ids;
 
diff --git a/root/components/rating-macros.tt b/root/components/rating-macros.tt
index 154774a..5455f58 100644
--- a/root/components/rating-macros.tt
+++ b/root/components/rating-macros.tt
@@ -9,7 +9,7 @@ END -%]
 [%- MACRO rating_rate_url(entity, rating) BLOCK;
     c.uri_for_action("/rating/rate", {
         entity_type => entity_type(entity),
-        entity_id   => entity.id,
+        entity_id   => entity.gid,
         rating      => rating * 20,
     });
 END -%]

commit 3614777669d554baf11d97869482b689b8ff5b71
Author: Oliver Charles <[email protected]>
Date:   Fri Jan 18 12:47:00 2013 +0000

    Add support for creating, viewing and editing works

diff --git a/lib/DBDefs/Default.pm b/lib/DBDefs/Default.pm
index 27e7df1..fb6e328 100644
--- a/lib/DBDefs/Default.pm
+++ b/lib/DBDefs/Default.pm
@@ -73,6 +73,8 @@ sub WEB_SERVER                { "www.musicbrainz.example.com" }
 sub LUCENE_SERVER             { "search.musicbrainz.org" }
 sub WEB_SERVER_USED_IN_EMAIL  { my $self = shift; $self->WEB_SERVER }
 
+sub DATA_ACCESS_SERVICE       { "http://localhost:8000" }
+
 ################################################################################
 # Mail Settings
 ################################################################################
diff --git a/lib/MusicBrainz/Server/Controller/Work.pm b/lib/MusicBrainz/Server/Controller/Work.pm
index 5862028..eba6f84 100644
--- a/lib/MusicBrainz/Server/Controller/Work.pm
+++ b/lib/MusicBrainz/Server/Controller/Work.pm
@@ -4,27 +4,31 @@ use Moose;
 BEGIN { extends 'MusicBrainz::Server::Controller'; }
 
 use MusicBrainz::Server::Constants qw(
-    $EDIT_WORK_CREATE
-    $EDIT_WORK_EDIT
     $EDIT_WORK_MERGE
-    $EDIT_WORK_ADD_ISWCS
-    $EDIT_WORK_REMOVE_ISWC
 );
+use MusicBrainz::Server::Entity::Work;
+use MusicBrainz::Server::Entity::Tree::Work;
 use MusicBrainz::Server::Translation qw( l );
+use MusicBrainz::Server::NES::Controller::Utils qw( create_edit create_update );
+
+__PACKAGE__->config(
+    tree_entity => 'MusicBrainz::Server::Entity::Tree::Work',
+);
 
 with 'MusicBrainz::Server::Controller::Role::Load' => {
-    model       => 'Work',
+    model       => 'NES::Work',
     entity_name => 'work',
 };
-with 'MusicBrainz::Server::Controller::Role::Annotation';
-with 'MusicBrainz::Server::Controller::Role::Alias';
+
 with 'MusicBrainz::Server::Controller::Role::Details';
-with 'MusicBrainz::Server::Controller::Role::Relationship';
-with 'MusicBrainz::Server::Controller::Role::Rating';
-with 'MusicBrainz::Server::Controller::Role::Tag';
 with 'MusicBrainz::Server::Controller::Role::EditListing';
-with 'MusicBrainz::Server::Controller::Role::Cleanup';
-with 'MusicBrainz::Server::Controller::Role::WikipediaExtract';
+# with 'MusicBrainz::Server::Controller::Role::Rating';
+# with 'MusicBrainz::Server::Controller::Role::Tag';
+# with 'MusicBrainz::Server::Controller::Role::Alias';
+# with 'MusicBrainz::Server::Controller::Role::Annotation';
+# with 'MusicBrainz::Server::Controller::Role::Relationship';
+# with 'MusicBrainz::Server::Controller::Role::Cleanup';
+# with 'MusicBrainz::Server::Controller::Role::WikipediaExtract';
 
 use aliased 'MusicBrainz::Server::Entity::ArtistCredit';
 
@@ -35,8 +39,8 @@ after 'load' => sub
     my ($self, $c) = @_;
 
     my $work = $c->stash->{work};
-    $c->model('Work')->load_meta($work);
-    $c->model('ISWC')->load_for_works($work);
+    # $c->model('Work')->load_meta($work);
+    # $c->model('ISWC')->load_for_works($work);
     if ($c->user_exists) {
         $c->model('Work')->rating->load_user_ratings($c->user->id, $work);
     }
@@ -50,13 +54,15 @@ sub show : PathPart('') Chained('load')
     $c->model('WorkType')->load($work);
     $c->model('Language')->load($work);
 
-    # need to call relationships for overview page
-    $self->relationships($c);
+    # Need to call relationships for overview page
+    # $self->relationships($c); NES
 
     $c->stash->{template} = 'work/index.tt';
 }
 
-for my $action (qw( relationships aliases tags details )) {
+# NES - originally:
+# for my $action (qw( relationships aliases tags details )) {
+for my $action (qw( details )) {
     after $action => sub {
         my ($self, $c) = @_;
         my $work = $c->stash->{work};
@@ -65,36 +71,24 @@ for my $action (qw( relationships aliases tags details )) {
     };
 }
 
-with 'MusicBrainz::Server::Controller::Role::Edit' => {
-    form           => 'Work',
-    edit_type      => $EDIT_WORK_EDIT,
-    edit_arguments => sub {
-        my ($self, $c, $work) = @_;
-
-        return (
-            post_creation => sub {
-                my ($edit, $form) = @_;
-
-                my @current_iswcs = $c->model('ISWC')->find_by_works($work->id);
-                my %current_iswcs = map { $_->iswc => 1 } @current_iswcs;
-                my @submitted = @{ $form->field('iswcs')->value };
-                my %submitted = map { $_ => 1 } @submitted;
-
-                my @added = grep { !exists($current_iswcs{$_}) } @submitted;
-                my @removed = grep { !exists($submitted{$_->iswc}) } @current_iswcs;
-
-                $self->_add_iswcs($c, $form, $work, @added) if @added;
-                $self->_remove_iswcs($c, $form, $work, @removed) if @removed;
-
-                if ((@added || @removed) && $c->stash->{makes_no_changes}) {
-                    $c->stash( makes_no_changes => 0 );
-                    $c->response->redirect(
-                        $c->uri_for_action($self->action_for('show'), [ $work->gid ]));
-                }
-            }
-        );
-    }
-};
+sub edit : Chained('load') {
+    my ($self, $c) = @_;
+
+    create_update(
+        $self, $c,
+        form => 'Work::Edit',
+        subject => $c->stash->{work},
+        build_tree => \&work_tree
+    );
+}
+
+sub work_tree {
+    my $values = shift;
+    return MusicBrainz::Server::Entity::Tree::Work->new(
+        work => MusicBrainz::Server::Entity::Work->new($values),
+        iswcs => $values->{iswcs} // []
+    );
+}
 
 with 'MusicBrainz::Server::Controller::Role::Merge' => {
     edit_type => $EDIT_WORK_MERGE,
@@ -123,52 +117,21 @@ after 'merge' => sub
     $c->model('ISWC')->load_for_works(@{ $c->stash->{to_merge} });
 };
 
-with 'MusicBrainz::Server::Controller::Role::Create' => {
-    form      => 'Work',
-    edit_type => $EDIT_WORK_CREATE,
-    edit_arguments => sub {
-        my ($self, $c) = @_;
-
-        return (
-            post_creation => sub {
-                my ($edit, $form) = @_;
-                my $work = $c->model('Work')->get_by_id($edit->entity_id);
-                my @iswcs = @{ $form->field('iswcs')->value };
-                $self->_add_iswcs($c, $form, $work, @iswcs) if scalar @iswcs;
-            }
-        );
-    }
-};
-
-sub _add_iswcs {
-    my ($self, $c, $form, $work, @iswcs) = @_;
-
-    $c->model('MB')->with_transaction(sub {
-        $self->_insert_edit(
-            $c, $form,
-            edit_type => $EDIT_WORK_ADD_ISWCS,
-            iswcs => [ map {
-                iswc => $_,
-                work => {
-                    id => $work->id,
-                    name => $work->name
-                }
-            }, @iswcs ]
-        );
-    });
-}
+sub create : Local Edit {
+    my ($self, $c) = @_;
 
-sub _remove_iswcs {
-    my ($self, $c, $form, $work, @iswcs) = @_;
-
-    $c->model('MB')->with_transaction(sub {
-        $self->_insert_edit(
-            $c, $form,
-            edit_type => $EDIT_WORK_REMOVE_ISWC,
-            iswc => $_,
-            work => $work
-        );
-    }) for @iswcs;
+    create_edit(
+        $self, $c,
+        form => 'Work',
+        on_post => sub {
+            my ($values, $edit) = @_;
+
+            return $c->model('NES::Work')->create(
+                $edit, $c->user,
+                work_tree($values)
+            );
+        }
+    );
 }
 
 1;
diff --git a/lib/MusicBrainz/Server/Data/NES/Edit.pm b/lib/MusicBrainz/Server/Data/NES/Edit.pm
new file mode 100644
index 0000000..c7b1996
--- /dev/null
+++ b/lib/MusicBrainz/Server/Data/NES/Edit.pm
@@ -0,0 +1,16 @@
+package MusicBrainz::Server::Data::NES::Edit;
+use Moose;
+
+use MusicBrainz::Server::Entity::NES::Edit;
+
+with 'MusicBrainz::Server::Data::Role::NES';
+
+sub open {
+    my $self = shift;
+    return MusicBrainz::Server::Entity::NES::Edit->new(
+        id => $self->request('/edit/open', {})->{ref}
+    );
+}
+
+__PACKAGE__->meta->make_immutable;
+1;
diff --git a/lib/MusicBrainz/Server/Data/NES/Work.pm b/lib/MusicBrainz/Server/Data/NES/Work.pm
new file mode 100644
index 0000000..3165b1b
--- /dev/null
+++ b/lib/MusicBrainz/Server/Data/NES/Work.pm
@@ -0,0 +1,122 @@
+package MusicBrainz::Server::Data::NES::Work;
+use Moose;
+
+use MusicBrainz::Server::Data::Utils qw( partial_date_to_hash );
+use MusicBrainz::Server::Entity::Work;
+use MusicBrainz::Server::WebService::Serializer::JSON::2::Utils qw( boolean );
+
+with 'MusicBrainz::Server::Data::Role::NES';
+
+sub create {
+    my ($self, $edit, $editor, $tree) = @_;
+
+    my $response = $self->request('/work/create', {
+        edit => $edit->id,
+        editor => $editor->id,
+        _work_tree($tree)
+    });
+
+    return $self->get_revision($response->{ref});
+}
+
+sub update {
+    my ($self, $edit, $editor, $base_revision, $tree) = @_;
+
+    die 'Need a base revision' unless $base_revision;
+
+    my $final_tree = do {
+        if( $tree->work_set && $tree->iswcs_set ) {
+            $tree
+        }
+        else {
+            my $original_tree = $self->view_tree($base_revision);
+
+            $original_tree->work($tree->work)
+                if ($tree->work_set);
+
+            $original_tree->iswcs($tree->iswcs)
+                if ($tree->iswcs_set);
+
+            $original_tree;
+        }
+    };
+
+    my $response = $self->request('/work/update', {
+        edit => $edit->id,
+        editor => $editor->id,
+        revision => $base_revision->revision_id,
+        _work_tree($final_tree)
+    });
+
+    return undef;
+}
+
+sub view_tree {
+    my ($self, $revision) = @_;
+
+    return MusicBrainz::Server::Entity::Tree::Work->new(
+        work => $revision,
+        iswcs => $self->get_iswcs($revision),
+    );
+}
+
+sub _work_tree {
+    my $tree = shift;
+
+    return (
+        work => do {
+            my $work = $tree->work;
+            {
+                 type => $work->type_id,
+                 language => $work->language_id,
+                 name => $work->name,
+                 comment => $work->comment
+            }
+        },
+        iswcs => [
+            map +{ iswc => $_ }, @{ $tree->iswcs }
+        ]
+    );
+}
+
+sub get_revision {
+    my ($self, $revision_id) = @_;
+    return _new_from_response(
+        $self->request('/work/view-revision', { revision => $revision_id }));
+}
+
+sub get_by_gid {
+    my ($self, $gid) = @_;
+    return _new_from_response(
+        $self->request('/work/find-latest', { mbid => $gid }))
+}
+
+sub _new_from_response {
+    my ($response) = @_;
+    return undef if keys %$response == 0;
+
+    my %data = %{ $response->{data} };
+    return MusicBrainz::Server::Entity::Work->new(
+        name => $data{name},
+        comment => $data{comment},
+        type_id => $data{type},
+        language_id => $data{language},
+
+        gid => $response->{mbid},
+        revision_id => $response->{revision}
+    );
+}
+
+sub tags {
+    my $self = shift;
+    $self->c->model('Work')->tags;
+}
+
+sub get_iswcs {
+    my ($self, $revision) = @_;
+    warn "Unimplemented";
+    return [];
+}
+
+__PACKAGE__->meta->make_immutable;
+1;
diff --git a/lib/MusicBrainz/Server/Data/Role/NES.pm b/lib/MusicBrainz/Server/Data/Role/NES.pm
new file mode 100644
index 0000000..1d19ec9
--- /dev/null
+++ b/lib/MusicBrainz/Server/Data/Role/NES.pm
@@ -0,0 +1,38 @@
+package MusicBrainz::Server::Data::Role::NES;
+use Moose::Role;
+
+with 'MusicBrainz::Server::Data::Role::Context';
+
+use Data::Dumper::Concise qw( Dumper );
+use Devel::Dwarn;
+use Encode;
+use JSON;
+use Try::Tiny;
+use Time::HiRes qw( gettimeofday tv_interval );
+
+sub request {
+    my ($self, $path, $body) = @_;
+
+    my $uri = DBDefs->DATA_ACCESS_SERVICE.$path;
+    my $content = to_json ($body, { canonical => 1 });
+
+    printf STDERR "> Request: $uri\n";
+    printf STDERR Dumper($body), "\n";
+
+    my $t0 = [ gettimeofday ];
+    my $response = $self->c->lwp->post($uri, Content => encode('utf8', $content));
+    my $t = tv_interval($t0);
+
+    return try {
+        printf STDERR "Response in ${t}s\n";
+        printf STDERR $response->content;
+        printf STDERR "\n\n";
+
+        return decode_json($response->content);
+    }
+    catch {
+        die 'Failed to decode response: ' . $response->content;
+    }
+}
+
+1;
diff --git a/lib/MusicBrainz/Server/Data/Work.pm b/lib/MusicBrainz/Server/Data/Work.pm
index 606a59d..47f38a8 100644
--- a/lib/MusicBrainz/Server/Data/Work.pm
+++ b/lib/MusicBrainz/Server/Data/Work.pm
@@ -122,33 +122,6 @@ sub load
     load_subobjects($self, 'work', @objs);
 }
 
-sub insert
-{
-    my ($self, @works) = @_;
-    my %names = $self->find_or_insert_names(map { $_->{name} } @works);
-    my $class = $self->_entity_class;
-    my @created;
-    for my $work (@works)
-    {
-        my $row = $self->_hash_to_row($work, \%names);
-        $row->{gid} = $work->{gid} || generate_gid();
-        push @created, $class->new(
-            id => $self->sql->insert_row('work', $row, 'id'),
-            gid => $row->{gid}
-        );
-    }
-    return @works > 1 ? @created : $created[0];
-}
-
-sub update
-{
-    my ($self, $work_id, $update) = @_;
-    return unless %{ $update // {} };
-    my %names = $self->find_or_insert_names($update->{name});
-    my $row = $self->_hash_to_row($update, \%names);
-    $self->sql->update_row('work', $row, { id => $work_id });
-}
-
 # Works can be unconditionally removed
 sub can_delete { 1 }
 
diff --git a/lib/MusicBrainz/Server/Entity/CoreEntity.pm b/lib/MusicBrainz/Server/Entity/CoreEntity.pm
index dbef7f6..23b6f27 100644
--- a/lib/MusicBrainz/Server/Entity/CoreEntity.pm
+++ b/lib/MusicBrainz/Server/Entity/CoreEntity.pm
@@ -2,9 +2,13 @@ package MusicBrainz::Server::Entity::CoreEntity;
 
 use Moose;
 
-extends 'MusicBrainz::Server::Entity';
 with 'MusicBrainz::Server::Entity::Role::Editable';
 
+has 'revision_id' => (
+    isa => 'Int',
+    is => 'ro',
+);
+
 has 'gid' => (
     is => 'rw',
     isa => 'Str'
diff --git a/lib/MusicBrainz/Server/Entity/Tree/Work.pm b/lib/MusicBrainz/Server/Entity/Tree/Work.pm
new file mode 100644
index 0000000..2e637b4
--- /dev/null
+++ b/lib/MusicBrainz/Server/Entity/Tree/Work.pm
@@ -0,0 +1,14 @@
+package MusicBrainz::Server::Entity::Tree::Work;
+use Moose;
+
+has work => (
+    is => 'rw',
+    predicate => 'work_set',
+);
+
+has iswcs => (
+    is => 'rw',
+    predicate => 'iswcs_set',
+);
+
+1;
diff --git a/lib/MusicBrainz/Server/Entity/Work.pm b/lib/MusicBrainz/Server/Entity/Work.pm
index 86b1dfd..fcafc9c 100644
--- a/lib/MusicBrainz/Server/Entity/Work.pm
+++ b/lib/MusicBrainz/Server/Entity/Work.pm
@@ -15,8 +15,8 @@ use MooseX::Types::Moose qw( ArrayRef Object Str );
 
 has 'type_id' => (
     is => 'rw',
-    isa => 'Int'
-    );
+    isa => 'Maybe[Int]'
+);
 
 has 'type' => (
     is => 'rw',
@@ -37,8 +37,8 @@ sub l_type_name
 
 has 'language_id' => (
     is => 'rw',
-    isa => 'Int'
-    );
+    isa => 'Maybe[Int]'
+);
 
 has 'language' => (
     is => 'rw',
diff --git a/lib/MusicBrainz/Server/Form/Work/Edit.pm b/lib/MusicBrainz/Server/Form/Work/Edit.pm
new file mode 100644
index 0000000..ae4085d
--- /dev/null
+++ b/lib/MusicBrainz/Server/Form/Work/Edit.pm
@@ -0,0 +1,12 @@
+package MusicBrainz::Server::Form::Work::Edit;
+use HTML::FormHandler::Moose;
+
+extends 'MusicBrainz::Server::Form::Work';
+
+has_field 'revision_id' => (
+    type => 'Integer',
+    required => 1
+);
+
+__PACKAGE__->meta->make_immutable;
+1;
diff --git a/lib/MusicBrainz/Server/NES/Controller/Utils.pm b/lib/MusicBrainz/Server/NES/Controller/Utils.pm
new file mode 100644
index 0000000..f066c42
--- /dev/null
+++ b/lib/MusicBrainz/Server/NES/Controller/Utils.pm
@@ -0,0 +1,72 @@
+package MusicBrainz::Server::NES::Controller::Utils;
+use strict;
+use warnings;
+
+use Sub::Exporter -setup => {
+    exports => [qw( create_edit create_update )]
+};
+
+sub create_edit {
+    my ($controller, $c, %opts) = @_;
+
+    my $form = do {
+        if (my $build_form = $opts{build_form}) {
+            $build_form->()
+        }
+        else {
+            my $form = do {
+                my %args = (
+                    ctx => $c,
+                );
+
+                $args{init_object} = $opts{subject}
+                    if defined $opts{subject};
+
+                $c->form(form => $opts{form}, %args);
+            }
+        }
+    };
+
+    if ($c->form_posted && $form->submitted_and_valid($c->req->body_params)) {
+        my $values = $form->values;
+        my $edit = $c->model('NES::Edit')->open;
+
+        my $work = $opts{on_post}->($values, $edit);
+
+        # NES:
+        # my $privs = $c->user->privileges;
+        # if ($c->user->is_auto_editor &&
+        #     $form->field('as_auto_editor') &&
+        #     !$form->field('as_auto_editor')->value) {
+        # }
+
+        $c->response->redirect(
+            $c->uri_for_action($controller->action_for('show'), [ $work->gid ]));
+    }
+    elsif (!$c->form_posted && %{ $c->req->query_params }) {
+        $form->process( params => $c->req->query_params );
+        $form->clear_errors;
+    }
+}
+
+sub create_update {
+    my ($controller, $c, %opts) = @_;
+    create_edit(
+        $controller, $c,
+        %opts,
+        on_post => sub {
+            my ($values, $edit) = @_;
+            my $revision = $c->model( $controller->{model} )->get_revision(
+                $values->{revision_id});
+
+            $c->model( $controller->{model} )->update(
+                $edit, $c->user, $revision,
+                $opts{build_tree}->($values, $revision)
+            );
+
+            return $revision;
+        }
+    );
+}
+
+1;
diff --git a/root/work/edit_form.tt b/root/work/edit_form.tt
index 446f126..bf23628 100644
--- a/root/work/edit_form.tt
+++ b/root/work/edit_form.tt
@@ -9,6 +9,8 @@
       [%- form_row_select(r, 'type_id', l('Type:')) -%]
       [%- form_row_select(r, 'language_id', l('Lyrics Language:')) -%]
       [%- form_row_text_list(r, 'iswcs', l('ISWCs:'), l('ISWC')) -%]
+
+      [% r.hidden(form.field('revision_id')) IF work.revision_id %]
     </fieldset>
 
     [%- INCLUDE 'forms/edit-note.tt' -%]

-----------------------------------------------------------------------


hooks/post-receive
-- 
mb_server