feat: handle unprotected session expiration (#779)
* feat: hide note contents if the protection expires when the protected note is open and wasn't edited for a while * feat: handle session expiration for opened protected note for both plain advanced editors * fix: if after canceling session expiry modal only one unprotected note stays selected, show its contents in the editor * refactor: handle session expiration for opened protected note (move the logic to web client) * feat: handle the case of selecting "Don't remember" option in session expiry dialog * test (WIP): add unit tests for protecting opened note after the session has expired * test: add remaining unit tests * refactor: move the opened note protection logic to "editor_view" * refactor: reviewer comments - don't rely on user signed-in/out status to require authentication for protected note - remove unnecessary async/awaits - better wording on ui * refactor: reviewer's comments: - use snjs method to check if "Don't remember" option is selected in authentication modal - move the constant to snjs - fix eslint error * refactor: avoid `any` type for `appEvent` payload * test: add unit tests * chore: update function name * refactor: use simpler protection session event types * refactor: protected access terminology * refactor: start counting idle timer after every edit (instead of counting by interval in spite of edits) * test: unit tests * style: don't give extra brightness to the "View Note"/"Authenticate" button on hover/focus * chore: bump snjs version * chore: put snjs "beta" version * fix: run protection timeout when the note is marked as protected * chore: snjs version bump * refactor: immediately lock the note if it's marked as "Protected" * refactor: rename component, directive and some props * refactor: remove extra check * refactor: rename the method * chore: update snjs version Co-authored-by: Mo Bitar <me@bitar.io>
This commit is contained in:
51
app/assets/javascripts/components/ProtectedNoteOverlay.tsx
Normal file
51
app/assets/javascripts/components/ProtectedNoteOverlay.tsx
Normal file
@@ -0,0 +1,51 @@
|
||||
import { AppState } from '@/ui_models/app_state';
|
||||
import { toDirective } from './utils';
|
||||
|
||||
type Props = {
|
||||
appState: AppState;
|
||||
onViewNote: () => void;
|
||||
hasProtectionSources: boolean;
|
||||
};
|
||||
|
||||
function ProtectedNoteOverlay({
|
||||
appState,
|
||||
onViewNote,
|
||||
hasProtectionSources,
|
||||
}: Props) {
|
||||
const instructionText = hasProtectionSources
|
||||
? 'Authenticate to view this note.'
|
||||
: 'Add a passcode or create an account to require authentication to view this note.';
|
||||
|
||||
return (
|
||||
<div className="flex flex-col items-center justify-center text-center max-w-md">
|
||||
<h1 className="text-2xl m-0 w-full">This note is protected</h1>
|
||||
<p className="text-lg mt-2 w-full">{instructionText}</p>
|
||||
<div className="mt-4 flex gap-3">
|
||||
{!hasProtectionSources && (
|
||||
<button
|
||||
className="sn-button small info"
|
||||
onClick={() => {
|
||||
appState.accountMenu.setShow(true);
|
||||
}}
|
||||
>
|
||||
Open account menu
|
||||
</button>
|
||||
)}
|
||||
<button
|
||||
className="sn-button small outlined normal-focus-brightness"
|
||||
onClick={onViewNote}
|
||||
>
|
||||
{hasProtectionSources ? 'Authenticate' : 'View Note'}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export const ProtectedNoteOverlayDirective = toDirective<Props>(
|
||||
ProtectedNoteOverlay,
|
||||
{
|
||||
onViewNote: '&',
|
||||
hasProtectionSources: '=',
|
||||
}
|
||||
);
|
||||
Reference in New Issue
Block a user