Redmine locale fix. Some RAL tweaks. Added line numbers to code-mirror.
authorŁukasz Rekucki <lrekucki@gmail.com>
Thu, 24 Sep 2009 15:30:21 +0000 (17:30 +0200)
committerŁukasz Rekucki <lrekucki@gmail.com>
Thu, 24 Sep 2009 15:30:21 +0000 (17:30 +0200)
22 files changed:
apps/api/handlers.py
apps/api/tests/data/testone/.hg/dirstate
apps/toolbar/templates/toolbar/toolbar.html
lib/wlrepo/__init__.py
lib/wlrepo/backend_mercurial.py
lib/wlrepo/tests/test_mercurial.py
project/settings.py
project/static/css/master.css
project/static/css/toolbar.css
project/static/js/editor.js
project/static/js/lib/codemirror/codemirror.js
project/templates/base.html
project/templates/explorer/panels/xmleditor.html
project/urls.py
redmine/redmine_publications/app/controllers/publications_controller.rb
redmine/redmine_publications/app/views/issues/_issue_form_pub.html.erb
redmine/redmine_publications/app/views/issues/_issue_view_pub.erb
redmine/redmine_publications/init.rb
redmine/redmine_publications/lib/redmine_publications/change_patch.rb [new file with mode: 0644]
redmine/redmine_publications/lib/redmine_publications/issue_patch.rb
redmine/redmine_publications/locales/en.yml [new file with mode: 0644]
redmine/redmine_publications/locales/pl.yml [new file with mode: 0644]

index 2f2bea1..9a54ce8 100644 (file)
@@ -64,6 +64,7 @@ class LibraryHandler(BaseHandler):
         if form.cleaned_data['generate_dc']:
             data = librarian.wrap_text(data, unicode(date.today()))
 
+        # TODO: what if the file exists ?
         doc = cab.create(form.cleaned_data['bookname'], initial_data=data)
         
         return {
@@ -124,6 +125,9 @@ class DocumentHandler(BaseHandler):
                 
         shared = lib.main_cabinet.retrieve(docid)
 
+        is_shared = document.ancestorof(shared)
+        # is_uptodate = is_shared or shared.ancestorof(document)
+
         result = {
             'name': document.name,
             'size': document.size,
@@ -132,12 +136,12 @@ class DocumentHandler(BaseHandler):
             'parts_url': reverse('docparts_view', args=[docid]),
             'latest_rev': document.shelf(),
             'latest_shared_rev': shared.shelf(),
-            #'shared': lib.isparentof(document, shared),
-            #'up_to_date': lib.isparentof(shared, document),
+            'shared': is_shared,
+            # 'up_to_date': is_uptodate,
         }
 
-        if request.GET.get('with_part', 'no') == 'yes':
-            result['parts'] = document.parts()
+        #if request.GET.get('with_part', 'no') == 'yes':
+        #    result['parts'] = document.parts()
 
         return result        
 
@@ -150,7 +154,9 @@ class DocumentTextHandler(BaseHandler):
     def read(self, request, docid):
         """Read document as raw text"""
         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
-        try:            
+        try:
+            # latest rev
+            # comment
             return lib.document(docid, request.user.username).read()
         except CabinetNotFound:
             return rc.NOT_HERE
@@ -158,6 +164,7 @@ class DocumentTextHandler(BaseHandler):
     def update(self, request, docid):
         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
         try:
+            # check latest REV
             data = request.PUT['contents']
             lib.document(docid, request.user.username).write(data)
             return rc.ALL_OK
index 121c271..e146f18 100644 (file)
Binary files a/apps/api/tests/data/testone/.hg/dirstate and b/apps/api/tests/data/testone/.hg/dirstate differ
index b0ee028..c4fcdcb 100644 (file)
@@ -8,7 +8,7 @@
     {% endfor %} 
     </span>
 
-    <div class="toolbar-tabs-container">
+    <div class="toolbar-tabs-container toolbar-buttons-container">
     <p>
         {% for group in toolbar_groups %}
         <button ui:group="{{ group.slug }}" {% if forloop.first %}class="active"{% endif %}>
index 210322d..1c1335e 100644 (file)
@@ -31,6 +31,10 @@ class Library(object):
         pass
 
 
+    def document(self, docid, user, part=None, shelve=None):
+        pass
+
+
 class Cabinet(object):
 
     def __init__(self, library, name=None, doc=None, user=None):
@@ -56,11 +60,11 @@ class Cabinet(object):
     def __str__(self):
         return "Cabinet(%s)" % self._name
 
-    def documents(self):
-        """Lists all documents and sub-documents in this cabinet."""
+    def parts(self):
+        """Lists all parts in this cabinet."""
         pass
     
-    def retrieve(self, parts=None, shelve=None):
+    def retrieve(self, part='xml', shelve=None):
         """Retrieve a document from a given shelve in the cabinet. If no
         part is given, the main document is retrieved. If no shelve is given,
         the top-most shelve is used.
@@ -70,7 +74,7 @@ class Cabinet(object):
         pass
 
     def create(self, name, initial_data=''):
-        """Create a new sub-document in the cabinet with the given name."""
+        """Create a new part in the cabinet with the given name."""
         pass
 
     @property
@@ -121,12 +125,25 @@ class Document(object):
     @property
     def parts(self):
         raise NotImplemented()
+    
+    def parentof(self, other):
+        return self.shelf().parentof(other.shelf())
+
+    def ancestorof(self, other):
+        return self.shelf().ancestorof(other.shelf())
 
 
 class Shelf(object):
 
     def __init__(self, lib):
-        self._library = lib        
+        self._library = lib
+
+
+    def parentof(self, other):
+        return False
+
+    def ancestorof(self, other):
+        return False
     
 #
 # Exception classes
index dfcef09..a082b8b 100644 (file)
@@ -68,8 +68,8 @@ class MercurialLibrary(wlrepo.Library):
     def main_cabinet(self):
         return self._maincab
 
-    def document(self, docid, user):
-        return self.cabinet(docid, user, create=False).retrieve()
+    def document(self, docid, user, part=None, shelve=None):
+        return self.cabinet(docid, user, create=False).retrieve(part=part, shelve=shelve)
 
     def cabinet(self, docid, user, create=False):
         docid = self._sanitize_string(docid)
@@ -248,10 +248,10 @@ class MercurialCabinet(wlrepo.Cabinet):
         else:
             raise ValueError("Provide either doc/user or branchname")
 
-    def shelf(self, selector=None):
+    def shelf(self):
         return self._library.shelf(self._branchname)
 
-    def documents(self):        
+    def parts(self):
         return self._execute_in_branch(action=lambda l, c: (e[1] for e in l._filelist()))
 
     def retrieve(self, part=None, shelf=None):
@@ -305,18 +305,22 @@ class MercurialCabinet(wlrepo.Cabinet):
 
         return self._library._transaction(write_mode=write, action=switch_action)
 
-    def _filename(self, part):
-        part = self._library._sanitize_string(part)
-        docid = None
 
-        if self._maindoc == '':
-            if part is None: rreeturn [None, None]
-            docid = part
-        else:
-            docid = self._maindoc + (('$' + part) if part else '')
+    def _filename(self, docid):
+        return self._partname(docid, 'xml')
+    
+    def _partname(self, docid, part):
+        docid = self._library._sanitize_string(part)
+        part = self._library._sanitize_string(part)
 
-        return docid, 'pub_' + docid + '.xml'
+        if part is None:
+            part = 'xml'
 
+        if self._maindoc == '' and docid is None:
+            return None
+            
+        return 'pub_' + docid + '.' + part
+            
     def _fileopener(self):
         return self._library._fileopener()
 
@@ -331,26 +335,33 @@ class MercurialCabinet(wlrepo.Cabinet):
 
 class MercurialDocument(wlrepo.Document):
 
-    def __init__(self, cabinet, name, fileid):
-        super(MercurialDocument, self).__init__(cabinet, name=name)
+    def __init__(self, cabinet, docid):
+        super(MercurialDocument, self).__init__(cabinet, name=docid)
         self._opener = self._cabinet._fileopener()
-        self._fileid = fileid
-        self.refresh()
+        self._docid = docid
+        self._ctxs = {}
+
+    def _ctx(self, part):
+        if not self._ctxs.has_key(part):            
+            self._ctxs[part] = self._cabinet._filectx(self._fileid())
+        return self._ctxs[part]
 
-    def refresh(self):
-        self._filectx = self._cabinet._filectx(self._fileid)        
+    def _fileid(self, part='xml'):
+        return self._cabinet._partname(self._docid, part)
 
-    def read(self):
-        return self._opener(self._filectx.path(), "r").read()
+    def read(self, part='xml'):       
+        return self._opener(self._ctx(part).path(), "r").read()
 
-    def write(self, data):
-        return self._opener(self._filectx.path(), "w").write(data)
+    def write(self, data, part='xml'):
+        return self._opener(self._ctx(part).path(), "w").write(data)
 
     def commit(self, message, user):
+        """Commit all parts of the document."""
         self.library._fileadd(self._fileid)
         self.library._commit(self._fileid, message, user)
 
     def update(self):
+        """Update parts of the document."""
         lock = self.library._lock()
         try:
             if self._cabinet.ismain():
@@ -453,15 +464,15 @@ class MercurialDocument(wlrepo.Document):
     def shared(self):
         return self.library.main_cabinet.retrieve(self._name)
 
-    def exists(self):
-        return self._cabinet.exists(self._fileid)
+    def exists(self, part='xml'):
+        return self._cabinet.exists(self._fileid(part))
 
     @property
     def size(self):
         return self._filectx.size()
     
     def shelf(self):
-        return MercurialShelf(self.library, self._filectx.node())
+        return self._cabinet.shelf()
 
     @property
     def last_modified(self):
index 1f708d6..9d37f9f 100644 (file)
@@ -51,7 +51,7 @@ def test_main_cabinet(library):
     mcab = library.main_cabinet
     assert_equal(mcab.maindoc_name, '')
 
-    doclist = mcab.documents()
+    doclist = mcab.parts()
     assert_equal( list(doclist), ['valid_file'])
 
 @temprepo('simple')
@@ -81,7 +81,7 @@ def test_create_document(library):
 @temprepo('branched')
 def test_switch_branch(library):
     tester_cab = library.cabinet("valid_file", "tester", create=False)
-    assert_equal( list(tester_cab.documents()), ['valid_file'])
+    assert_equal( list(tester_cab.parts()), ['valid_file'])
 
 @raises(wlrepo.CabinetNotFound)
 @temprepo('branched')
@@ -232,5 +232,5 @@ def test_merge_personal_to_default(library):
 @temprepo('clean')
 def test_create_branch(library):   
     tester_cab = library.cabinet("anotherone", "tester", create=True)
-    assert_equal( list(tester_cab.documents()), ['anotherone'])  
+    assert_equal( list(tester_cab.parts()), ['anotherone'])
 
index 178a104..0e9ba8d 100644 (file)
@@ -114,6 +114,7 @@ INSTALLED_APPS = (
     'explorer',
     'toolbar',
     'api',
+    'wysiwyg',
 )
 
 
index de79989..b413b2c 100644 (file)
@@ -341,4 +341,15 @@ text#commit-dialog-message {
 
 #split-dialog .container-box fieldset {
     margin: 0.5em;
+}
+
+.CodeMirror-line-numbers
+{
+    text-align: right;
+    padding-top: 0.4em;
+    padding-right: 2px;
+    width: 28px;
+    font-size: 10pt;
+    background: black;
+    color: white;
 }
\ No newline at end of file
index a54dc55..03cb2d2 100644 (file)
     padding: 0px;
 }
 
-.toolbar-tabs-container button.active {
-    background: #DDD;
-}
-
 .toolbar-buttons-container {
     background: #DDD;
     padding-top: 2px;
     background: inherit;    
 }
 
-/* 
-.toolbar, .toolbar ol {
-    display: block;
-    margin: 0;
-    padding: 0;
-    background-color: #CCC;
-    border-top: 1px solid #AAA;
-}
-
-.toolbar-tabs li {
-    font-size: 14px;
-    display: block;
-    float: left;
-    margin: 4px 0 -1px 4px;
-    padding: 2px 10px 0 10px;
-    background-color: #CCC;
-    border: 1px solid #AAA;
-    border-radius-topleft: 8px;
-    border-radius-topright: 8px;
-    -moz-border-radius-topleft: 8px;
-    -moz-border-radius-topright: 8px;
-    -webkit-border-top-left-radius: 8px;
-    -webkit-border-top-right-radius: 8px;
-}
-
-.toolbar-tabs {
-    height: 21px;
+.toolbar-tabs-container > p {
+    background: #CCC;
 }
 
-.toolbar-tabs li:hover, .toolbar-tabs li.active {
-    cursor: default;
-    background-color: #EEE;
-    border-bottom: 1px solid #EEE;
+.toolbar-tabs-container > p button {
+    background: #CCC;
 }
 
-.toolbar-buttons {
-    background-color: #EEE;
-    border-bottom: 1px solid #AAA;
-    z-index: 71;
-}
-
-.toolbar-buttons li {
-    display: block;
-    font-size: 12px;
-    padding: 1px 8px;
-    margin: 4px;
-    border-radius: 10px;
-    -moz-border-radius: 10px;
-    -webkit-border-radius: 8px;
-    float: left;
-}
-
-.toolbar-buttons li:hover {
-    background-color: #777;
-    color: #FFF;
-    cursor: default;
-} */
-
+.toolbar-tabs-container button.active {
+    background: #DDD;
+}
\ No newline at end of file
index 94b4ca9..79b7fa9 100644 (file)
@@ -152,9 +152,7 @@ Panel.prototype.connectToolbar = function()
     // move the extra
     var extra_buttons = $('span.panel-toolbar-extra button', toolbar);
     var placeholder = $('div.panel-toolbar span.panel-toolbar-extra > span', this.wrap);
-    placeholder.replaceWith(extra_buttons);    
-
-    var action_buttons = $('button', extra_buttons);
+    placeholder.replaceWith(extra_buttons);       
 
     // connect group-switch buttons
     var group_buttons = $('*.toolbar-tabs-container button', toolbar);
@@ -185,7 +183,7 @@ Panel.prototype.connectToolbar = function()
     });
 
     // connect action buttons
-    var allbuttons = $.makeArray(action_buttons);
+    var allbuttons = $.makeArray(extra_buttons);
     $.merge(allbuttons,
         $.makeArray($('*.toolbar-button-groups-container button', toolbar)) );
         
index 97e2657..c8e5ddc 100644 (file)
@@ -55,20 +55,34 @@ var CodeMirror = (function(){
 
   function wrapLineNumberDiv(place) {
     return function(node) {
+        
       var container = document.createElement("DIV"),
           nums = document.createElement("DIV"),
           scroller = document.createElement("DIV");
-      container.style.position = "relative";
+      
       nums.style.position = "absolute";
-      nums.style.height = "100%";
+      nums.style.height = "100%";      
       if (nums.style.setExpression) {
         try {nums.style.setExpression("height", "this.previousSibling.offsetHeight + 'px'");}
         catch(e) {} // Seems to throw 'Not Implemented' on some IE8 versions
       }
       nums.style.top = "0px";
-      nums.style.overflow = "hidden";
+      nums.style.overflow = "hidden";      
+
+      container.style.position = "absolute";
+      container.style.left = "0px";
+      container.style.right = "0px";
+      container.style.bottom = "0px";
+      container.style.top = "0px";
+
+      node.style.position = "absolute";
+      node.style.top = "0px";
+      node.style.right = "0px";
+      node.style.bottom = "0px";
+      node.style.left = "16px"
+
       place(container);
-      container.appendChild(node);
+      container.appendChild(node);     
       container.appendChild(nums);
       scroller.className = "CodeMirror-line-numbers";
       nums.appendChild(scroller);
@@ -77,7 +91,7 @@ var CodeMirror = (function(){
 
   function applyLineNumbers(frame) {
     var win = frame.contentWindow, doc = win.document,
-        nums = frame.nextSibling, scroller = nums.firstChild;
+        nums = frame.parentNode.nextSibling, scroller = nums.firstChild;
 
     var nextNum = 1, barWidth = null;
     function sizeBar() {
@@ -92,7 +106,7 @@ var CodeMirror = (function(){
 
       if (nums.offsetWidth != barWidth) {
         barWidth = nums.offsetWidth;
-        nums.style.left = "-" + (frame.parentNode.style.marginLeft = barWidth + "px");
+        // nums.style.left = "-" + (frame.parentNode.style.marginLeft = barWidth + "px");
       }
     }
     function update() {
@@ -125,8 +139,8 @@ var CodeMirror = (function(){
     frame.frameBorder = 0;
     frame.src = "javascript:false;";
     frame.style.border = "0";
-    frame.style.width = options.width;
-    frame.style.height = options.height;
+    frame.style.width = "100%";
+    frame.style.height = "100%";
     // display: block occasionally suppresses some Firefox bugs, so we
     // always add it, redundant as it sounds.
     frame.style.display = "block";
@@ -135,8 +149,40 @@ var CodeMirror = (function(){
       var node = place;
       place = function(n){node.appendChild(n);};
     }
-    if (options.lineNumbers) place = wrapLineNumberDiv(place);
-    place(frame);
+
+    var iframe_container = document.createElement("DIV");
+    iframe_container.appendChild(frame);
+
+    var content_wrapper = document.createElement("DIV");
+    content_wrapper.appendChild(iframe_container);
+    content_wrapper.style.position = 'relative';
+    content_wrapper.className = 'CodeMirror-content-wrapper';
+    
+    iframe_container.style.position = 'absolute';
+    iframe_container.style.top = '0px';
+    iframe_container.style.right = '0px';
+    iframe_container.style.bottom = '0px';
+    iframe_container.style.left = '28px';
+    
+    if (options.lineNumbers) {
+       var nums = document.createElement("DIV"),
+          scroller = document.createElement("DIV");
+
+        nums.style.position = "absolute";
+        nums.style.height = "100%";
+
+        nums.style.top = "0px";
+        nums.style.left = "0px";
+        nums.style.overflow = "hidden";
+
+        scroller.className = "CodeMirror-line-numbers";
+        nums.appendChild(scroller);
+        content_wrapper.appendChild(nums);
+
+        iframe_container.style.right = nums.width;        
+    }   
+    
+    place(content_wrapper);
 
     // Link back to this object, so that the editor can fetch options
     // and add a reference to itself.
index dacd73b..48ad036 100644 (file)
@@ -6,7 +6,7 @@
         <title>{% block title %}Platforma Redakcyjna{% block subtitle %}{% endblock subtitle %}{% endblock title%}</title>
         <link rel="stylesheet" href="{{ STATIC_URL }}css/master.css" type="text/css" />
         <script src="{{ STATIC_URL }}js/lib/jquery.js" type="text/javascript" charset="utf-8"></script>
-               <script src="{{ STATIC_URL }}js/lib/jquery.logging.js" type="text/javascript" charset="utf-8"></script>
+       <script src="{{ STATIC_URL }}js/lib/jquery.logging.js" type="text/javascript" charset="utf-8"></script>
         {% block extrahead %}
         {% endblock %}
     </head>
@@ -21,6 +21,6 @@
        </div>
     <div id="content">{% block maincontent %} {% endblock %}</div>
 
-    {% block extrabody %} {% endblock %}
+    {% block extrabody %}{% endblock %}
     </body>
 </html>
index 4ec75d2..74a6877 100644 (file)
@@ -17,8 +17,11 @@ panel_hooks = {
        var texteditor = CodeMirror.fromTextArea(textareaId, {            
             parserfile: 'parsexml.js',
             path: "{{STATIC_URL}}js/lib/codemirror/",
+            width: 'auto',
             stylesheet: "{{STATIC_URL}}css/xmlcolors.css",
             parserConfig: {useHTMLKludges: false},
+            textWrapping: false,
+            lineNumbers: true,
             onChange: function() {
                self.fireEvent('contentChanged');
             },
@@ -33,7 +36,9 @@ panel_hooks = {
             }
         })
 
-        $(texteditor.frame).css({width: '100%', height: '100%'});    
+        $('.CodeMirror-content-wrapper').css({
+            width: '100%', height: '100%' });
+                    
         this.texteditor = texteditor;
         self._endload();       
     },
index 2c1fab7..c889631 100644 (file)
@@ -1,3 +1,5 @@
+# -*- coding: utf-8 -*-
+
 from django.conf.urls.defaults import *
 from django.contrib import admin
 from django.conf import settings
@@ -42,7 +44,10 @@ urlpatterns = patterns('',
     url(r'^accounts/login/$', 'django.contrib.auth.views.login', {'redirect_field_name': 'next'}),
     url(r'^accounts/logout/$', 'django.contrib.auth.views.logout', {'next_page': '/'}),
 
-    # Our uber-restful api
+    # Prototypes
+    url(r'^wysiwyg-proto/', include('wysiwyg.urls')),
+
+    # Our über-restful api
     url(r'^api/', include('api.urls') ),
 )
 
index 6c1e734..ebf735b 100644 (file)
@@ -19,28 +19,28 @@ class PublicationsController < ApplicationController
     Publication.delete_all()
     repos = Repository.all
     if repos
-    repos.each do |repo|
-      repo_status = []
-      if repo.entries
-      repo.entries.each do |entry|
-        match = entry.path.match(regexp)
-        if match
-          Publication.find_or_create_by_name(:name => match[1],
-            :source_file => entry.path, :repository_id => repo.id)
-          repo_status += [{:path => entry.path, :match => match[1], :matched => true}]
-        else
-          repo_status += [{:path => entry.path, :match =>nil, :matched => false}]
+      repos.each do |repo|
+        repo_status = []
+        if repo.entries
+          repo.entries.each do |entry|
+            match = entry.path.match(regexp)
+            if match
+              Publication.find_or_create_by_name(:name => match[1],
+                :source_file => entry.path, :repository_id => repo.id)
+              repo_status += [{:path => entry.path, :match => match[1], :matched => true}]
+            else
+              repo_status += [{:path => entry.path, :match =>nil, :matched => false}]
+            end
+          end
+          @match_status += [{:repo => repo, :status => repo_status}]
         end
       end
-      @match_status += [{:repo => repo, :status => repo_status}]
-      end
-    end
        
-    respond_to do |format|
-      format.html
-      format.xml { render :xml => @match_status}
-      format.json { render :json => @match_status }
-    end
+      respond_to do |format|
+        format.html
+        format.xml { render :xml => @match_status}
+        format.json { render :json => @match_status }
+      end
     end
   end
 
@@ -52,7 +52,7 @@ class PublicationsController < ApplicationController
     @issues = Issue.all(:joins => joins, :conditions =>  conditions)
 
     respond_to do |fmt| 
-       fmt.json { render :json => @issues, :callback => params[:callback] }
+      fmt.json { render :json => @issues, :callback => params[:callback] }
     end
   end
 
index f0f7a1a..ebb903c 100644 (file)
@@ -1,5 +1,5 @@
 <div>
-<p><label for="issue_source_files">Publication(s)</label>
+<p><label for="issue_source_files"><%= l(:field_publications) %>:</label>
 <input type='text' id='publications' name="publications" size="50"
        value='<%= @issue.publication_names.join(', ') %>' />
 </div>
index 26ce997..a22c78b 100644 (file)
@@ -1,5 +1,5 @@
 <tr>
-    <td><b>Publication(s)</b></td>
+    <td><b><%= l(:field_publications) %>:</b></td>
     <td>
 <% @issue.publication_names.each  do |pub| %>
       <a href="<%= Setting.plugin_redmine_publications[:editorurl].sub(':pubid', pub) %>"><%= pub %></a><br />
index 0aa6f07..4298f60 100644 (file)
@@ -11,6 +11,10 @@ Dispatcher.to_prepare :redmine_publications do
   unless Issue.included_modules.include? RedminePublications::IssuePatch
     Issue.send(:include, RedminePublications::IssuePatch)
   end
+
+  unless Change.included_modules.include? RedminePublications::ChangePatch
+    Change.send(:include, RedminePublications::ChangePatch)
+  end
 end
 
 require_dependency 'issue_publication_hook'
diff --git a/redmine/redmine_publications/lib/redmine_publications/change_patch.rb b/redmine/redmine_publications/lib/redmine_publications/change_patch.rb
new file mode 100644 (file)
index 0000000..41ea959
--- /dev/null
@@ -0,0 +1,38 @@
+module RedminePublications
+  # Patches Redmine's Issues dynamically. Adds a +after_save+ filter.
+
+  module ChangePatch
+    def self.included(base) # :nodoc:
+      base.extend(ClassMethods)
+
+      base.send(:include, InstanceMethods)
+
+      # Same as typing in the class
+      base.class_eval do
+        unloadable # Send unloadable so it will not be unloaded in development
+        after_save :update_publication
+      end
+
+    end
+
+    module ClassMethods
+    end
+
+    module InstanceMethods
+
+      def update_publication
+        if self.action == 'A'
+          regexp = Regexp.new(Setting.plugin_redmine_publications[:pattern])
+          match = self.path.match(regexp)
+          Rails.logger.info('[INFO] Adding publication: "' << match[1])
+          Publication.find_or_create_by_name(:name => match[1],
+            :source_file => self.path, :repository_id => self.changeset.repository.id )
+        end      
+      end
+      
+    end
+    
+  end
+
+
+end
index c108799..bd1f73e 100644 (file)
@@ -11,8 +11,8 @@ module RedminePublications
       base.class_eval do
         unloadable # Send unloadable so it will not be unloaded in development
  
-       validate :check_relations
-       after_save :update_relations
+        validate :check_relations
+        after_save :update_relations
       end
  
     end
@@ -23,55 +23,55 @@ module RedminePublications
     module InstanceMethods
 
       def publication_names    
-       if not @pubnames
-         self.publications.map { |pub| pub.name }
+        if not @pubnames
+          self.publications.map { |pub| pub.name }
         else
-         @pubnames        
-       end
+          @pubnames
+        end
       end
 
       def publication_names=(value)
-       @pubnames = value.sort!
+        @pubnames = value.sort!
       end
 
       def publications
         Publication.all( 
-         :joins => 
-           "JOIN issue_publications ON (issue_publications.publication_id = publications.id)",
-         :conditions =>
-           ["issue_publications.issue_id = ? ", self.id] )     
+          :joins =>
+            "JOIN issue_publications ON (issue_publications.publication_id = publications.id)",
+          :conditions =>
+            ["issue_publications.issue_id = ? ", self.id] )
       end
 
       def check_relations
-       current_names = self.publication_names
-       non_existant = []
+        current_names = self.publication_names
+        non_existant = []
 
-       pubs =  Publication.find_all_by_name(current_names).map {|i| i.name}
-       missing = current_names.select {|name| not pubs.include?name }
+        pubs =  Publication.find_all_by_name(current_names).map {|i| i.name}
+        missing = current_names.select {|name| not pubs.include?name }
 
-       if not missing.empty?
-         errors.add("publications", "Missing publication(s): " + missing.join(', '))
-       end
-     end
+        if not missing.empty?
+          errors.add("publications", "Missing publication(s): " + missing.join(', '))
+        end
+      end
 
-     def update_relations
-       old = self.publications
-       current_names = self.publication_names
-       Rails.logger.info('[INFO] Updating relations: old= ' << old.inspect << ' current=' << current_names.inspect)
+      def update_relations
+        old = self.publications
+        current_names = self.publication_names
+        Rails.logger.info('[INFO] Updating relations: old= ' << old.inspect << ' current=' << current_names.inspect)
 
-       # delete unused relations
-       deleted = old.select { |v| not (current_names.include?(v.name)) }
-       deleted.each do |pub| 
-         IssuePublication.delete_all(["issue_publications.issue_id = ? AND issue_publications.publication_id = ?", self.id, pub.id])
-       end
+        # delete unused relations
+        deleted = old.select { |v| not (current_names.include?(v.name)) }
+        deleted.each do |pub|
+          IssuePublication.delete_all(["issue_publications.issue_id = ? AND issue_publications.publication_id = ?", self.id, pub.id])
+        end
 
-       current_names.each do |name|    
-           pub = Publication.find_by_name(name)
-           IssuePublication.find_or_create_by_publication_id_and_issue_id(pub.id, self.id)
-       end
+        current_names.each do |name|
+          pub = Publication.find_by_name(name)
+          IssuePublication.find_or_create_by_publication_id_and_issue_id(pub.id, self.id)
+        end
 
         return true
-     end
+      end
 
     end
   end
diff --git a/redmine/redmine_publications/locales/en.yml b/redmine/redmine_publications/locales/en.yml
new file mode 100644 (file)
index 0000000..3932ef2
--- /dev/null
@@ -0,0 +1,3 @@
+## YAML Template.
+en:
+  field_publications: Publications
diff --git a/redmine/redmine_publications/locales/pl.yml b/redmine/redmine_publications/locales/pl.yml
new file mode 100644 (file)
index 0000000..2bf0783
--- /dev/null
@@ -0,0 +1,3 @@
+## YAML Template.
+pl:
+  field_publications: Publikacje