View | Details | Raw Unified | Return to bug 17268
Collapse All | Expand All

(-)a/Koha/REST/V1/AdvancedEditorMacro.pm (-1 lines)
Lines 150-156 sub add_shared { Link Here
150
        return $c->render( status  => 403,
150
        return $c->render( status  => 403,
151
                           openapi => { error => "To create private macros you must use advancededitor" } );
151
                           openapi => { error => "To create private macros you must use advancededitor" } );
152
    }
152
    }
153
154
    return try {
153
    return try {
155
        my $macro = Koha::AdvancedEditorMacro->new( _to_model( $c->validation->param('body') ) );
154
        my $macro = Koha::AdvancedEditorMacro->new( _to_model( $c->validation->param('body') ) );
156
        $macro->store;
155
        $macro->store;
(-)a/koha-tmpl/intranet-tmpl/prog/en/includes/cateditor-ui.inc (-43 / +178 lines)
Lines 693-728 require( [ 'koha-backend', 'search', 'macros', 'marc-editor', 'marc-record', 'pr Link Here
693
    }
693
    }
694
694
695
    //> Macro functions
695
    //> Macro functions
696
    function loadMacro( name ) {
696
    var canCreatePublic = "[% CAN_user_editcatalogue_create_shared_macros | html %]";
697
    var canDeletePublic = "[% CAN_user_editcatalogue_delete_shared_macros | html %]";
698
699
    function deleteMacro( id ){
700
        $( '#macro-list' ).empty();
701
        var shared = macroEditor.activeMacroShared;
702
        var id = macroEditor.activeMacroId;
703
        macroEditor.activeMacroId = null;
704
        api_url = "/api/v1/advancededitormacros/";
705
        if( shared ) { api_url += "shared/" }
706
        let options = {
707
            url: api_url + id,
708
            method: "DELETE",
709
            contentType: "application/json",
710
        };
711
        $.ajax(options)
712
            .then(function(result) {
713
                humanMsg.displayAlert( _("Macro successfully deleted") );
714
                showSavedMacros();
715
            })
716
            .fail(function(err) {
717
                humanMsg.displayAlert( _("Failed to delete macro:") + err.responseText, { className: 'humanError' } );
718
            });
719
    }
720
721
722
    function loadMacro( name, id, shared ) {
697
        $( '#macro-list li' ).removeClass( 'active' );
723
        $( '#macro-list li' ).removeClass( 'active' );
724
        $(".macro_shared").prop("checked",false).hide();
725
        $("#delete-macro").prop("disabled",true);
726
        macroEditor.setOption( 'readOnly', false );
698
        macroEditor.activeMacro = name;
727
        macroEditor.activeMacro = name;
728
        macroEditor.activeMacroId = id;
699
729
700
        if ( !name ) {
730
        if ( !name ) {
701
            macroEditor.setValue( '' );
731
            macroEditor.setValue( '' );
702
            return;
732
            return;
703
        }
733
        }
734
        $( '#macro-list li[data-name="' + name + '"][data-id="' + id + '"]' ).addClass( 'active' );
735
        api_url = "/api/v1/advancededitormacros/";
736
        if( shared ) { api_url += "shared/" }
737
        let options = {
738
            url: api_url + id,
739
            method: "GET",
740
            contentType: "application/json",
741
        };
742
        $.ajax(options)
743
            .then(function(result) {
744
                macroEditor.setValue( result.macro_text );
745
                $(".macro_shared").show();
746
                if( result.shared ){
747
                    $(".macro_shared").prop("checked",true);
748
                    if( canCreatePublic ){
749
                        macroEditor.setOption( 'readOnly', false );
750
                    } else {
751
                        macroEditor.setOption( 'readOnly', true );
752
                    }
753
                    if( canDeletePublic ){
754
                        $("#delete-macro").prop("disabled",false);
755
                    }
756
                } else {
757
                    macroEditor.setOption( 'readOnly', false );
758
                    $("#delete-macro").prop("disabled",false);
759
                }
760
                macroEditor.activeMacroShared = result.shared;
761
            })
762
            .fail(function(err) {
763
                humanMsg.displayAlert( _("Failed to load macros:") + err.responseText, { className: 'humanError' } );
764
            });
704
765
705
        $( '#macro-list li[data-name="' + name + '"]' ).addClass( 'active' );
706
        var macro = Preferences.user.macros[name];
707
        macroEditor.setValue( macro.contents );
708
        macroEditor.setOption( 'readOnly', false );
709
        $( '#macro-format' ).val( macro.format || 'its' );
710
        if ( macro.history ) macroEditor.setHistory( macro.history );
711
    }
712
713
    function storeMacro( name, macro ) {
714
        if ( macro ) {
715
            Preferences.user.macros[name] = macro;
716
        } else {
717
            delete Preferences.user.macros[name];
718
        }
719
720
        Preferences.Save( [% logged_in_user.borrowernumber | html %] );
721
    }
766
    }
722
767
723
    function showSavedMacros( macros ) {
768
    function convertOldMacros(){
724
        var scrollTop = $('#macro-list').scrollTop();
769
        $("#convert-macros").remove();
725
        $( '#macro-list' ).empty();
726
        var macro_list = $.map( Preferences.user.macros, function( macro, name ) {
770
        var macro_list = $.map( Preferences.user.macros, function( macro, name ) {
727
            return $.extend( { name: name }, macro );
771
            return $.extend( { name: name }, macro );
728
        } );
772
        } );
Lines 730-773 require( [ 'koha-backend', 'search', 'macros', 'marc-editor', 'marc-record', 'pr Link Here
730
            return a.name.localeCompare(b.name);
774
            return a.name.localeCompare(b.name);
731
        } );
775
        } );
732
        $.each( macro_list, function( undef, macro ) {
776
        $.each( macro_list, function( undef, macro ) {
733
            var $li = $( '<li data-name="' + macro.name + '"><a href="#">' + macro.name + '</a><ol class="macro-info"></ol></li>' );
777
            let options = {
734
            $li.click( function() {
778
                url: "/api/v1/advancededitormacros/",
735
                loadMacro(macro.name);
779
                method: "POST",
736
                return false;
780
                contentType: "application/json",
737
            } );
781
                data: JSON.stringify({
738
            if ( macro.name == macroEditor.activeMacro ) $li.addClass( 'active' );
782
                    name: macro.name,
739
            var modified = macro.modified && new Date(macro.modified);
783
                    patron_id: [% logged_in_user.borrowernumber | html %],
740
            $li.find( '.macro-info' ).append(
784
                    macro_text: macro.contents,
741
                '<li><span class="label">' + _("Last changed:") + '</span>' +
785
                    shared: 0
742
                ( modified ? ( modified.toLocaleDateString() + ', ' + modified.toLocaleTimeString() ) : _("never") ) + '</li>'
786
                })
743
            );
787
            };
744
            $('#macro-list').append($li);
788
            $.ajax(options)
789
                .then(function(undef, result) {
790
                    delete Preferences.user.macros[macro.name];
791
                    Preferences.Save( [% logged_in_user.borrowernumber | html %] );
792
                })
793
                .fail(function(err) {
794
                    humanMsg.displayAlert( _("Failed to create macro:") + err.responseText, { className: 'humanError' } );
795
                });
745
        } );
796
        } );
797
        showSavedMacros();
798
    }
799
800
    function showSavedMacros( macros ) {
801
        var scrollTop = $('#macro-list').scrollTop();
802
        $( '#macro-list' ).empty();
803
        $("#convert-macros").remove();
804
        if( Preferences.user.macros.length ){
805
            $convert = $( '<button class="btn btn-default" id="convert-macros" title="Convert browser storage macros"><i class="fa fa-adjust"></i> Convert old macros</button>' );
806
            $convert.click( function(){
807
                if( !confirm( _("This will retreieve macros stored in the brower, save them in the database, and delete them from the browser. Proceed?") ) ){
808
                    return;
809
                }
810
                convertOldMacros();
811
            });
812
            $("#macro-toolbar").prepend($convert);
813
        }
814
        let options = {
815
            url: "/api/v1/advancededitormacros/",
816
            method: "GET",
817
            contentType: "application/json",
818
        };
819
        $.ajax(options)
820
            .then(function(result) {
821
                    $.each(result,function( undef, macro ){
822
                        var $li = $( '<li data-name="' + macro.name + '" data-id="' + macro.macro_id + '"><a href="#">'+ macro.macro_id + ' - ' + macro.name + '</a><ol class="macro-info"></ol></li>' );
823
                        if ( macro.macro_id == macroEditor.activeMacroId ) $li.addClass( 'active' );
824
                        $li.click( function() {
825
                            loadMacro(macro.name, macro.macro_id, macro.shared);
826
                            return false;
827
                        } );
828
                        $('#macro-list').append($li);
829
                    });
830
            })
831
            .fail(function(err) {
832
                humanMsg.displayAlert( _("Failed to load macros:") + err.responseText, { className: 'humanError' } );
833
            });
746
        var $new_li = $( '<li class="new-macro"><a href="#">' + _("New macro...") + '</a></li>' );
834
        var $new_li = $( '<li class="new-macro"><a href="#">' + _("New macro...") + '</a></li>' );
747
        $new_li.click( function() {
835
        $new_li.click( function() {
748
            // TODO: make this a bit less retro
836
            // TODO: make this a bit less retro
749
            var name = prompt(_("Please enter the name for the new macro:"));
837
            var name = prompt(_("Please enter the name for the new macro:"));
750
            if (!name) return;
838
            if (!name) return;
751
839
752
            if ( !Preferences.user.macros[name] ) storeMacro( name, { format: "rancor", contents: "" } );
840
//            if ( !Preferences.user.macros[name] ) storeMacro( name, { format: "rancor", contents: "" } );
753
            showSavedMacros();
841
            let options = {
754
            loadMacro( name );
842
                url: "/api/v1/advancededitormacros/",
843
                method: "POST",
844
                contentType: "application/json",
845
                data: JSON.stringify({
846
                    name: name,
847
                    patron_id: [% logged_in_user.borrowernumber | html %],
848
                    macro_text: "",
849
                    shared: 0
850
                })
851
            };
852
            $.ajax(options)
853
                .then(function(undef, result) {
854
                    showSavedMacros();
855
                    loadMacro( result.name, result.macro_id );
856
                })
857
                .fail(function(err) {
858
                    humanMsg.displayAlert( _("Failed to create macro:") + err.responseText, { className: 'humanError' } );
859
                });
755
        } );
860
        } );
756
        $('#macro-list').append($new_li);
861
        $('#macro-list').append($new_li);
757
        $('#macro-list').scrollTop(scrollTop);
862
        $('#macro-list').scrollTop(scrollTop);
758
    }
863
    }
759
864
760
    function saveMacro() {
865
    function saveMacro(shared) {
761
        var name = macroEditor.activeMacro;
866
        var name = macroEditor.activeMacro;
867
        var macro_id = macroEditor.activeMacroId;
868
        var was_shared = macroEditor.activeMacroShared;
762
869
763
        if ( !name || macroEditor.savedGeneration == macroEditor.changeGeneration() ) return;
870
        if ( !name || macroEditor.savedGeneration == macroEditor.changeGeneration() && was_shared == shared ) return;
764
871
765
        macroEditor.savedGeneration = macroEditor.changeGeneration();
872
        macroEditor.savedGeneration = macroEditor.changeGeneration();
766
        storeMacro( name, { contents: macroEditor.getValue(), modified: (new Date()).valueOf(), history: macroEditor.getHistory(), format: $('#macro-format').val() } );
873
        api_url = "/api/v1/advancededitormacros/";
767
        $('#macro-save-message').text(_("Saved"));
874
        if( shared || was_shared ) { api_url += "shared/" }
875
876
        let options = {
877
            url: api_url + macro_id,
878
            method: "PUT",
879
            contentType: "application/json",
880
            data: JSON.stringify({
881
                name: name,
882
                patron_id: [% logged_in_user.borrowernumber | html %],
883
                macro_text: macroEditor.getValue(),
884
                shared: shared
885
            })
886
        };
887
        $.ajax(options)
888
            .then(function(result) {
889
                $('#macro-save-message').text(_("Saved"));
890
                macroEditor.activeMacroShared = shared;
891
            })
892
            .fail(function(err) {
893
                humanMsg.displayAlert( _("Failed to save macro:") + err.responseText, { className: 'humanError' } );
894
            });
768
        showSavedMacros();
895
        showSavedMacros();
769
    }
896
    }
770
897
898
    $(".macro_shared").change(function(){
899
        if(this.checked){
900
            saveMacro(1);
901
        } else {
902
            saveMacro(0);
903
        }
904
    });
905
906
    // END Macro functions
907
771
    $(document).ready( function() {
908
    $(document).ready( function() {
772
        // Editor setup
909
        // Editor setup
773
        editor = new MARCEditor( {
910
        editor = new MARCEditor( {
Lines 844-850 require( [ 'koha-backend', 'search', 'macros', 'marc-editor', 'marc-record', 'pr Link Here
844
981
845
                if ( saveTimeout ) clearTimeout( saveTimeout );
982
                if ( saveTimeout ) clearTimeout( saveTimeout );
846
                saveTimeout = setTimeout( function() {
983
                saveTimeout = setTimeout( function() {
847
                    saveMacro();
984
                    saveMacro(macroEditor.activeMacroShared);
848
985
849
                    saveTimeout = null;
986
                    saveTimeout = null;
850
                }, 500 );
987
                }, 500 );
Lines 1005-1013 require( [ 'koha-backend', 'search', 'macros', 'marc-editor', 'marc-record', 'pr Link Here
1005
1142
1006
        $('#delete-macro').click( function() {
1143
        $('#delete-macro').click( function() {
1007
            if ( !macroEditor.activeMacro || !confirm( _("Are you sure you want to delete this macro?") ) ) return;
1144
            if ( !macroEditor.activeMacro || !confirm( _("Are you sure you want to delete this macro?") ) ) return;
1008
1145
            deleteMacro();
1009
            storeMacro( macroEditor.activeMacro, undefined );
1010
            showSavedMacros();
1011
            loadMacro( undefined );
1146
            loadMacro( undefined );
1012
1147
1013
            return false;
1148
            return false;
(-)a/koha-tmpl/intranet-tmpl/prog/en/modules/cataloguing/editor.tt (-1 / +6 lines)
Lines 265-270 Link Here
265
            <button class="btn btn-default" id="run-macro" title="Run and edit macros"><i class="fa fa-play"></i> Run macro</button>
265
            <button class="btn btn-default" id="run-macro" title="Run and edit macros"><i class="fa fa-play"></i> Run macro</button>
266
            <button class="btn btn-default" id="delete-macro" title="Delete macro"><i class="fa fa-trash"></i> Delete macro</button>
266
            <button class="btn btn-default" id="delete-macro" title="Delete macro"><i class="fa fa-trash"></i> Delete macro</button>
267
            <label for="macro-format">Format: </label> <select id="macro-format"></select>
267
            <label for="macro-format">Format: </label> <select id="macro-format"></select>
268
            <label class="macro_shared" for="public" style="display:none;">Public macro:</label>
269
            [% IF CAN_user_editcatalogue_create_shared_macros %]
270
                <input class="macro_shared" type="checkbox" name="public" style="display:none;"/>
271
            [% ELSE %]
272
                <input class="macro_shared" type="checkbox" name="public" style="display:none;" disabled/>
273
            [% END %]
268
            <div id="macro-save-message"></div>
274
            <div id="macro-save-message"></div>
269
        </div>
275
        </div>
270
    </div>
276
    </div>
271
- 

Return to bug 17268