mirror of
https://github.com/scinote-eln/scinote-web.git
synced 2024-09-20 14:45:56 +08:00
Merge branch 'develop' into kb_SCI-10761_data-e2e-protocol-templates
This commit is contained in:
commit
86c99feb39
|
@ -201,23 +201,27 @@ var zebraPrint = (function() {
|
|||
});
|
||||
}
|
||||
|
||||
updateProgressModalData(progressModal, printData.printer_name, PRINTER_STATUS_SEARCH, PRINTER_STATUS_SEARCH);
|
||||
device = findDevice(printData.printer_name);
|
||||
if (dataZebra?.responseJSON?.labels?.length && printData.number_of_copies > 0) {
|
||||
updateProgressModalData(progressModal, printData.printer_name, PRINTER_STATUS_SEARCH, PRINTER_STATUS_SEARCH);
|
||||
device = findDevice(printData.printer_name);
|
||||
|
||||
getPrinterStatus(device).then((device) => {
|
||||
if (device.status === I18n.t('label_printers.modal_printing_status.printer_status.ready')) {
|
||||
print(
|
||||
device,
|
||||
progressModal,
|
||||
printData.number_of_copies,
|
||||
printData.printer_name,
|
||||
dataZebra.responseJSON.labels,
|
||||
0,
|
||||
);
|
||||
} else {
|
||||
updateProgressModalData(progressModal, printData.printer_name, PRINTER_STATUS_ERROR, PRINTER_STATUS_ERROR);
|
||||
}
|
||||
});
|
||||
getPrinterStatus(device).then((device) => {
|
||||
if (device.status === I18n.t('label_printers.modal_printing_status.printer_status.ready')) {
|
||||
print(
|
||||
device,
|
||||
progressModal,
|
||||
printData.number_of_copies,
|
||||
printData.printer_name,
|
||||
dataZebra.responseJSON.labels,
|
||||
0
|
||||
);
|
||||
} else {
|
||||
updateProgressModalData(progressModal, printData.printer_name, PRINTER_STATUS_ERROR, PRINTER_STATUS_ERROR);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
updateProgressModalData(progressModal, printData.printer_name, PRINTER_STATUS_ERROR, PRINTER_STATUS_ERROR);
|
||||
}
|
||||
}).fail(() => {
|
||||
HelperModule.flashAlertMsg(I18n.t('repository_row.modal_print_label.general_error'), 'danger');
|
||||
});
|
||||
|
|
|
@ -323,7 +323,7 @@ class AssetsController < ApplicationController
|
|||
end
|
||||
|
||||
ActiveRecord::Base.transaction do
|
||||
old_name = @asset.name
|
||||
old_name = @asset.file_name
|
||||
@asset.last_modified_by = current_user
|
||||
@asset.rename_file(new_name)
|
||||
@asset.save!
|
||||
|
@ -332,7 +332,7 @@ class AssetsController < ApplicationController
|
|||
when Step
|
||||
message_items = { old_name:, new_name:, user: current_user.id }
|
||||
message_items[:my_module] = @assoc.protocol.my_module.id if @assoc.protocol.in_module?
|
||||
|
||||
@asset.parent.touch
|
||||
log_step_activity(
|
||||
"#{@assoc.protocol.in_module? ? 'task' : 'protocol'}_step_asset_renamed",
|
||||
@assoc,
|
||||
|
|
|
@ -210,13 +210,19 @@ class Users::RegistrationsController < Devise::RegistrationsController
|
|||
def regenerate_api_key
|
||||
current_user.regenerate_api_key!
|
||||
|
||||
redirect_to edit_user_registration_path
|
||||
redirect_to(edit_user_registration_path(anchor: 'api-key'),
|
||||
flash: {
|
||||
success: t('users.registrations.edit.api_key.generated')
|
||||
})
|
||||
end
|
||||
|
||||
def revoke_api_key
|
||||
current_user.revoke_api_key!
|
||||
|
||||
redirect_to edit_user_registration_path
|
||||
redirect_to(edit_user_registration_path(anchor: 'api-key'),
|
||||
flash: {
|
||||
success: t('users.registrations.edit.api_key.revoked')
|
||||
})
|
||||
end
|
||||
|
||||
protected
|
||||
|
|
|
@ -255,6 +255,7 @@ export default {
|
|||
});
|
||||
},
|
||||
initZebraPrinter() {
|
||||
this.printers = this.printers.filter((printer) => !printer.id.startsWith('zebra'));
|
||||
this.zebraPrinters = zebraPrint.init($('#LabelPrinterSelector'), {
|
||||
clearSelectorOnFirstDevice: false,
|
||||
appendDevice: (device) => {
|
||||
|
|
|
@ -44,8 +44,7 @@
|
|||
<Teleport to="body">
|
||||
<RenameAttachmentModal
|
||||
v-if="renameModal"
|
||||
:url_path="attachment.attributes.urls.rename"
|
||||
:fileName="attachment.attributes.file_name"
|
||||
:attachment="attachment"
|
||||
@attachment:update="$emit('attachment:update', $event)"
|
||||
@close="renameModal = false"
|
||||
/>
|
||||
|
@ -170,18 +169,18 @@ export default {
|
|||
data_e2e: 'e2e-BT-attachmentOptions-move'
|
||||
});
|
||||
}
|
||||
if (this.attachment.attributes.urls.rename) {
|
||||
menu.push({
|
||||
text: this.i18n.t('assets.context_menu.rename'),
|
||||
emit: 'rename'
|
||||
});
|
||||
}
|
||||
if (this.attachment.attributes.urls.duplicate) {
|
||||
menu.push({
|
||||
text: this.i18n.t('assets.context_menu.duplicate'),
|
||||
emit: 'duplicate'
|
||||
});
|
||||
}
|
||||
if (this.attachment.attributes.urls.rename) {
|
||||
menu.push({
|
||||
text: this.i18n.t('assets.context_menu.rename'),
|
||||
emit: 'rename'
|
||||
});
|
||||
}
|
||||
if (this.attachment.attributes.urls.delete) {
|
||||
menu.push({
|
||||
text: this.i18n.t('assets.context_menu.delete'),
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
<template>
|
||||
<div ref="modal" @keydown.esc="close" class="modal" id="renameAttachmentModal" tabindex="-1" role="dialog">
|
||||
<div class="modal-dialog modal-md" role="document">
|
||||
<div class="modal-dialog modal-sm" role="document">
|
||||
<div class="modal-content">
|
||||
<div class="modal-header">
|
||||
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><i class="sn-icon sn-icon-close"></i></button>
|
||||
|
@ -9,9 +9,14 @@
|
|||
</h4>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<p>{{ i18n.t('assets.from_clipboard.file_name')}}</p>
|
||||
<div class="sci-input-container" :class="{ 'error': error }" :data-error-text="error">
|
||||
<input ref="input" v-model="name" type="text" class="sci-input-field" @keyup.enter="renameAttachment(name)" required="true" />
|
||||
<label class="sci-label">
|
||||
{{ i18n.t('assets.from_clipboard.file_name')}}
|
||||
</label>
|
||||
<div class="flex gap-1 items-center">
|
||||
<div class="sci-input-container" :class="{ 'error': error }" :data-error-text="error">
|
||||
<input ref="input" v-model="name" type="text" class="sci-input-field" @keyup.enter="renameAttachment(name)" required="true" />
|
||||
</div>
|
||||
<div class="shrink-0">.{{ this.attachment.attributes.file_extension }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
|
@ -31,14 +36,10 @@ export default {
|
|||
name: 'RenameAttachmentModal',
|
||||
mixins: [modalMixin],
|
||||
props: {
|
||||
url_path: {
|
||||
type: String,
|
||||
attachment: {
|
||||
type: Object,
|
||||
required: true
|
||||
},
|
||||
fileName: {
|
||||
type: String,
|
||||
required: true
|
||||
}
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
|
@ -47,7 +48,7 @@ export default {
|
|||
};
|
||||
},
|
||||
created() {
|
||||
this.name = this.fileName;
|
||||
this.name = this.attachment.attributes.file_name_without_extension;
|
||||
},
|
||||
watch: {
|
||||
name() {
|
||||
|
@ -71,10 +72,9 @@ export default {
|
|||
return;
|
||||
}
|
||||
|
||||
const payload = { asset: { name: newName } };
|
||||
|
||||
const payload = { asset: { name: `${newName}.${this.attachment.attributes.file_extension}` } };
|
||||
try {
|
||||
const response = await axios.patch(this.url_path, payload);
|
||||
const response = await axios.patch(this.attachment.attributes.urls.rename, payload);
|
||||
this.$emit('attachment:update', response.data.data);
|
||||
this.close();
|
||||
} catch (error) {
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
|
||||
module SearchableModel
|
||||
extend ActiveSupport::Concern
|
||||
DATA_VECTOR_ATTRIBUTES = ['asset_text_data.data_vector', 'tables.data_vector'].freeze
|
||||
|
||||
included do
|
||||
# Helper function for relations that
|
||||
|
@ -174,21 +175,19 @@ module SearchableModel
|
|||
|
||||
def self.create_query_clause(attrs, index, negate, query_clauses, value_hash, phrase, current_operator)
|
||||
phrase = sanitize_sql_like(phrase)
|
||||
phrase = Regexp.escape(phrase)
|
||||
exact_match = phrase =~ /^".*"$/
|
||||
like = exact_match ? '~' : 'ILIKE'
|
||||
phrase = exact_match ? "(^|\\s)#{phrase[1..-2]}(\\s|$)" : "%#{phrase}%"
|
||||
|
||||
where_clause = (attrs.map.with_index do |a, i|
|
||||
where_clause = (attrs.map.with_index do |attribute, i|
|
||||
i = (index * attrs.count) + i
|
||||
if %w(repository_rows.id repository_number_values.data).include?(a)
|
||||
"#{a} IS NOT NULL AND (((#{a})::text) #{like} :t#{i}) OR "
|
||||
elsif defined?(model::PREFIXED_ID_SQL) && a == model::PREFIXED_ID_SQL
|
||||
"#{a} IS NOT NULL AND (#{a} #{like} :t#{i}) OR "
|
||||
elsif ['asset_text_data.data_vector', 'tables.data_vector'].include?(a)
|
||||
"#{a} @@ plainto_tsquery(:t#{i}) OR "
|
||||
if %w(repository_rows.id repository_number_values.data).include?(attribute)
|
||||
"#{attribute} IS NOT NULL AND (((#{attribute})::text) #{like} :t#{i}) OR "
|
||||
elsif defined?(model::PREFIXED_ID_SQL) && attribute == model::PREFIXED_ID_SQL
|
||||
"#{attribute} IS NOT NULL AND (#{attribute} #{like} :t#{i}) OR "
|
||||
elsif DATA_VECTOR_ATTRIBUTES.include?(attribute)
|
||||
"#{attribute} @@ to_tsquery(:t#{i}) OR "
|
||||
else
|
||||
"#{a} IS NOT NULL AND ((trim_html_tags(#{a})) #{like} :t#{i}) OR "
|
||||
"#{attribute} IS NOT NULL AND ((trim_html_tags(#{attribute})) #{like} :t#{i}) OR "
|
||||
end
|
||||
end).join[0..-5]
|
||||
|
||||
|
@ -199,9 +198,20 @@ module SearchableModel
|
|||
end
|
||||
|
||||
value_hash.merge!(
|
||||
(attrs.map.with_index do |_, i|
|
||||
(attrs.map.with_index do |attribute, i|
|
||||
i = (index * attrs.count) + i
|
||||
["t#{i}".to_sym, phrase]
|
||||
|
||||
new_phrase = exact_match ? phrase[1..-2] : phrase
|
||||
if DATA_VECTOR_ATTRIBUTES.include?(attribute)
|
||||
new_phrase = Regexp.escape(new_phrase.gsub(/[!()&|:<]/, ' ').strip).split(/\s+/)
|
||||
new_phrase.map! { |t| "#{t}:*" } unless exact_match
|
||||
new_phrase = new_phrase.join('&').tr('\'', '"')
|
||||
else
|
||||
new_phrase = Regexp.escape(new_phrase)
|
||||
new_phrase = exact_match ? "(^|\\s)#{new_phrase}(\\s|$)" : "%#{new_phrase}%"
|
||||
end
|
||||
|
||||
["t#{i}".to_sym, new_phrase]
|
||||
end).to_h
|
||||
)
|
||||
end
|
||||
|
|
|
@ -516,6 +516,7 @@ class User < ApplicationRecord
|
|||
def regenerate_api_key!
|
||||
update!(
|
||||
api_key: SecureRandom.urlsafe_base64(33),
|
||||
api_key_created_at: Time.current,
|
||||
api_key_expires_at: Constants::API_KEY_EXPIRES_IN.from_now
|
||||
)
|
||||
end
|
||||
|
|
|
@ -9,7 +9,7 @@ class AssetSerializer < ActiveModel::Serializer
|
|||
include ApplicationHelper
|
||||
|
||||
attributes :file_name, :file_extension, :view_mode, :icon, :urls, :updated_at_formatted,
|
||||
:file_size, :medium_preview, :large_preview, :asset_type, :wopi,
|
||||
:file_size, :medium_preview, :large_preview, :asset_type, :wopi, :file_name_without_extension,
|
||||
:wopi_context, :pdf_previewable, :file_size_formatted, :asset_order,
|
||||
:updated_at, :metadata, :image_editable, :image_context, :pdf, :attached, :parent_type,
|
||||
:edit_version_range
|
||||
|
@ -23,6 +23,10 @@ class AssetSerializer < ActiveModel::Serializer
|
|||
object.render_file_name
|
||||
end
|
||||
|
||||
def file_name_without_extension
|
||||
File.basename(object.file_name, '.*')
|
||||
end
|
||||
|
||||
def file_extension
|
||||
File.extname(object.file_name)[1..]
|
||||
end
|
||||
|
|
|
@ -1,11 +1,19 @@
|
|||
<div class="mb-8">
|
||||
<h3><%= t("users.registrations.edit.api_key.title") %></h3>
|
||||
<h3 id="api-key"><%= t("users.registrations.edit.api_key.title") %></h3>
|
||||
<p>
|
||||
<%= t("users.registrations.edit.api_key.description") %>
|
||||
</p>
|
||||
<% if current_user.api_key %>
|
||||
<div class="api-key-display">
|
||||
<%= text_field_tag :api_key, current_user.api_key, class: "p-3 mb-2 w-full", disabled: "disabled" %>
|
||||
<div class="form-group sci-input-container right-icon !w-1/2">
|
||||
<%= password_field_tag :api_key,
|
||||
current_user.api_key,
|
||||
name: 'api_key',
|
||||
class: 'form-control sci-input-field !text-sn-black !font-mono !cursor-text',
|
||||
disabled: 'disabled'
|
||||
%>
|
||||
<i class="sn-icon sn-icon-visibility-show show-password" style="cursor: pointer; z-index: 10"></i>
|
||||
</div>
|
||||
<% if current_user.api_key_expires_at < Time.current %>
|
||||
<p class="">
|
||||
<%= t("users.registrations.edit.api_key.expired") %>
|
||||
|
|
|
@ -13,5 +13,5 @@ Rails.application.configure do
|
|||
|
||||
config.x.core_api_v2_enabled = ENV['CORE_API_V2_ENABLED'] || false
|
||||
|
||||
config.x.core_api_key_enabled = ENV['CORE_API_KEY_ENABLED'] || false
|
||||
config.x.core_api_key_enabled = ENV['CORE_API_KEY_ENABLED'] == 'true'
|
||||
end
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
module PermissionExtends
|
||||
module TeamPermissions
|
||||
%w(
|
||||
NONE
|
||||
READ
|
||||
MANAGE
|
||||
USERS_MANAGE
|
||||
|
@ -17,6 +18,7 @@ module PermissionExtends
|
|||
|
||||
module ProtocolPermissions
|
||||
%w(
|
||||
NONE
|
||||
READ
|
||||
READ_ARCHIVED
|
||||
MANAGE
|
||||
|
@ -27,6 +29,7 @@ module PermissionExtends
|
|||
|
||||
module ReportPermissions
|
||||
%w(
|
||||
NONE
|
||||
READ
|
||||
MANAGE
|
||||
USERS_MANAGE
|
||||
|
@ -35,6 +38,7 @@ module PermissionExtends
|
|||
|
||||
module ProjectPermissions
|
||||
%w(
|
||||
NONE
|
||||
READ
|
||||
READ_ARCHIVED
|
||||
MANAGE
|
||||
|
@ -52,6 +56,7 @@ module PermissionExtends
|
|||
|
||||
module ExperimentPermissions
|
||||
%w(
|
||||
NONE
|
||||
READ
|
||||
READ_ARCHIVED
|
||||
MANAGE
|
||||
|
@ -65,6 +70,7 @@ module PermissionExtends
|
|||
|
||||
module MyModulePermissions
|
||||
%w(
|
||||
NONE
|
||||
READ
|
||||
READ_ARCHIVED
|
||||
ACTIVITIES_READ
|
||||
|
@ -106,6 +112,7 @@ module PermissionExtends
|
|||
|
||||
module RepositoryPermissions
|
||||
%w(
|
||||
NONE
|
||||
READ
|
||||
READ_ARCHIVED
|
||||
MANAGE
|
||||
|
@ -132,7 +139,7 @@ module PermissionExtends
|
|||
ExperimentPermissions.constants.map { |const| ExperimentPermissions.const_get(const) } +
|
||||
MyModulePermissions.constants.map { |const| MyModulePermissions.const_get(const) } +
|
||||
RepositoryPermissions.constants.map { |const| RepositoryPermissions.const_get(const) }
|
||||
)
|
||||
).reject { |p| p.end_with?("_none") }
|
||||
|
||||
NORMAL_USER_PERMISSIONS = [
|
||||
TeamPermissions::PROJECTS_CREATE,
|
||||
|
|
|
@ -2832,6 +2832,8 @@ en:
|
|||
regenerate: "Regenerate"
|
||||
revoke: "Revoke"
|
||||
expired: "This key has expired!"
|
||||
generated: "API key generated!"
|
||||
revoked: "API key revoked!"
|
||||
new:
|
||||
head_title: "Sign up"
|
||||
team_name_label: "Team name"
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
class AddApiKeyCreatedAtToUsers < ActiveRecord::Migration[7.0]
|
||||
def change
|
||||
add_column :users, :api_key_created_at, :timestamp
|
||||
end
|
||||
end
|
22
yarn.lock
22
yarn.lock
|
@ -2255,9 +2255,9 @@ axios@^0.21.1:
|
|||
follow-redirects "^1.14.0"
|
||||
|
||||
axios@^1.6.0:
|
||||
version "1.6.8"
|
||||
resolved "https://registry.yarnpkg.com/axios/-/axios-1.6.8.tgz#66d294951f5d988a00e87a0ffb955316a619ea66"
|
||||
integrity sha512-v/ZHtJDU39mDpyBoFVkETcd/uNdxrWRrg3bKpOKzXFA6Bvqopts6ALSMU3y6ijYxbw2B+wPrIv46egTzJXCLGQ==
|
||||
version "1.7.2"
|
||||
resolved "https://registry.yarnpkg.com/axios/-/axios-1.7.2.tgz#b625db8a7051fbea61c35a3cbb3a1daa7b9c7621"
|
||||
integrity sha512-2A8QhOMrbomlDuiLeK9XibIBzuHeRcqqNOHp0Cyp5EoJ1IFDh+XZH3A6BkXtv0K4gFGCI0Y4BM7B1wOEi0Rmgw==
|
||||
dependencies:
|
||||
follow-redirects "^1.15.6"
|
||||
form-data "^4.0.0"
|
||||
|
@ -5384,10 +5384,10 @@ minipass@^3.0.0, minipass@^3.1.1, minipass@^3.1.6:
|
|||
dependencies:
|
||||
yallist "^4.0.0"
|
||||
|
||||
minipass@^4.0.0:
|
||||
version "4.2.5"
|
||||
resolved "https://registry.yarnpkg.com/minipass/-/minipass-4.2.5.tgz#9e0e5256f1e3513f8c34691dd68549e85b2c8ceb"
|
||||
integrity sha512-+yQl7SX3bIT83Lhb4BVorMAHVuqsskxRdlmO9kTpyukp8vsm2Sn/fUOV9xlnG8/a5JsypJzap21lz/y3FBMJ8Q==
|
||||
minipass@^5.0.0:
|
||||
version "5.0.0"
|
||||
resolved "https://registry.yarnpkg.com/minipass/-/minipass-5.0.0.tgz#3e9788ffb90b694a5d0ec94479a45b5d8738133d"
|
||||
integrity sha512-3FnjYuehv9k6ovOEbyOswadCDPX1piCfhV8ncmYtHOjuPwylVWsghTLo7rabjC3Rx5xD4HDx8Wm1xnMF7S5qFQ==
|
||||
|
||||
minizlib@^2.1.1, minizlib@^2.1.2:
|
||||
version "2.1.2"
|
||||
|
@ -7331,13 +7331,13 @@ tar-stream@^3.1.5:
|
|||
streamx "^2.15.0"
|
||||
|
||||
tar@^6.1.11, tar@^6.1.2:
|
||||
version "6.1.13"
|
||||
resolved "https://registry.yarnpkg.com/tar/-/tar-6.1.13.tgz#46e22529000f612180601a6fe0680e7da508847b"
|
||||
integrity sha512-jdIBIN6LTIe2jqzay/2vtYLlBHa3JF42ot3h1dW8Q0PaAG4v8rm0cvpVePtau5C6OKXGGcgO9q2AMNSWxiLqKw==
|
||||
version "6.2.1"
|
||||
resolved "https://registry.yarnpkg.com/tar/-/tar-6.2.1.tgz#717549c541bc3c2af15751bea94b1dd068d4b03a"
|
||||
integrity sha512-DZ4yORTwrbTj/7MZYq2w+/ZFdI6OZ/f9SFHR+71gIVUZhOQPHzVCLpvRnPgyaMpfWxxk/4ONva3GQSyNIKRv6A==
|
||||
dependencies:
|
||||
chownr "^2.0.0"
|
||||
fs-minipass "^2.0.0"
|
||||
minipass "^4.0.0"
|
||||
minipass "^5.0.0"
|
||||
minizlib "^2.1.1"
|
||||
mkdirp "^1.0.3"
|
||||
yallist "^4.0.0"
|
||||
|
|
Loading…
Reference in a new issue