Spaces:
Sleeping
Sleeping
| import { EditorView, Decoration, type DecorationSet, ViewPlugin, WidgetType } from '@codemirror/view'; | |
| // Create a proper WidgetType class for the masked text | |
| class MaskedTextWidget extends WidgetType { | |
| constructor(private readonly _value: string) { | |
| super(); | |
| } | |
| eq(other: MaskedTextWidget) { | |
| return other._value === this._value; | |
| } | |
| toDOM() { | |
| const span = document.createElement('span'); | |
| span.textContent = '*'.repeat(this._value.length); | |
| span.className = 'cm-masked-text'; | |
| return span; | |
| } | |
| ignoreEvent() { | |
| return false; | |
| } | |
| } | |
| export function createEnvMaskingExtension(getFilePath: () => string | undefined) { | |
| return ViewPlugin.fromClass( | |
| class { | |
| decorations: DecorationSet; | |
| constructor(view: EditorView) { | |
| this.decorations = this.buildDecorations(view); | |
| } | |
| update(update: { docChanged: boolean; view: EditorView; viewportChanged: boolean }) { | |
| if (update.docChanged || update.viewportChanged) { | |
| this.decorations = this.buildDecorations(update.view); | |
| } | |
| } | |
| buildDecorations(view: EditorView) { | |
| const filePath = getFilePath(); | |
| const isEnvFile = filePath?.endsWith('.env') || filePath?.includes('.env.') || filePath?.includes('/.env'); | |
| if (!isEnvFile) { | |
| return Decoration.none; | |
| } | |
| const decorations: any[] = []; | |
| const doc = view.state.doc; | |
| for (let i = 1; i <= doc.lines; i++) { | |
| const line = doc.line(i); | |
| const text = line.text; | |
| // Match lines with KEY=VALUE format | |
| const match = text.match(/^([^=]+)=(.+)$/); | |
| if (match && !text.trim().startsWith('#')) { | |
| const [, key, value] = match; | |
| const valueStart = line.from + key.length + 1; | |
| // Create a decoration that replaces the value with asterisks | |
| decorations.push( | |
| Decoration.replace({ | |
| inclusive: true, | |
| widget: new MaskedTextWidget(value), | |
| }).range(valueStart, line.to), | |
| ); | |
| } | |
| } | |
| return Decoration.set(decorations); | |
| } | |
| }, | |
| { | |
| decorations: (v) => v.decorations, | |
| }, | |
| ); | |
| } | |