Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions client/pubspec.lock
Original file line number Diff line number Diff line change
Expand Up @@ -359,7 +359,7 @@ packages:
path: "../packages/flet"
relative: true
source: path
version: "0.84.0"
version: "0.83.1"
flet_ads:
dependency: "direct main"
description:
Expand Down Expand Up @@ -911,10 +911,10 @@ packages:
dependency: transitive
description:
name: matcher
sha256: "12956d0ad8390bbcc63ca2e1469c0619946ccb52809807067a7020d57e647aa6"
sha256: dc0b7dc7651697ea4ff3e69ef44b0407ea32c487a39fff6a4004fa585e901861
url: "https://pub.dev"
source: hosted
version: "0.12.18"
version: "0.12.19"
material_color_utilities:
dependency: transitive
description:
Expand Down Expand Up @@ -1628,10 +1628,10 @@ packages:
dependency: transitive
description:
name: test_api
sha256: "93167629bfc610f71560ab9312acdda4959de4df6fac7492c89ff0d3886f6636"
sha256: "8161c84903fd860b26bfdefb7963b3f0b68fee7adea0f59ef805ecca346f0c7a"
url: "https://pub.dev"
source: hosted
version: "0.7.9"
version: "0.7.10"
torch_light:
dependency: transitive
description:
Expand Down
Original file line number Diff line number Diff line change
@@ -1,14 +1,25 @@
import 'package:flutter/widgets.dart';
import 'package:flutter_code_editor/flutter_code_editor.dart' as fce;
import 'package:highlight/languages/json.dart';

import 'json_analyzer.dart';

class FletCodeController extends fce.CodeController {
FletCodeController({
super.text,
super.language,
});
// ISSUE-6312: Use a dedicated analyzer for JSON so invalid JSON can surface
// gutter markers instead of falling back to the default fold-only analyzer.
FletCodeController({super.text, super.language})
: super(analyzer: _analyzerForLanguage(language));

bool autocompletionEnabled = false;

static fce.AbstractAnalyzer _analyzerForLanguage(dynamic language) {
// ISSUE-6312: Keep existing behavior for other languages and only switch
// JSON to the custom analyzer added for this bug fix.
return language != json
? const fce.DefaultLocalAnalyzer()
: const JsonLocalAnalyzer();
}

@override
Future<void> generateSuggestions() async {
if (!autocompletionEnabled) {
Expand Down Expand Up @@ -44,10 +55,7 @@ class FletCodeController extends fce.CodeController {
extentOffset: endSelectionPosition,
);

value = TextEditingValue(
text: replacedText,
selection: adjustedSelection,
);
value = TextEditingValue(text: replacedText, selection: adjustedSelection);

popupController.hide();
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import 'dart:convert';

import 'package:flutter_code_editor/flutter_code_editor.dart' as fce;

// ISSUE-6312: JSON syntax errors were not converted into editor issues, so the
// gutter had nothing to render. This analyzer adds real JSON validation.
class JsonLocalAnalyzer extends fce.AbstractAnalyzer {
const JsonLocalAnalyzer();

static const _defaultAnalyzer = fce.DefaultLocalAnalyzer();

@override
Future<fce.AnalysisResult> analyze(fce.Code code) async {
final issues = (await _defaultAnalyzer.analyze(code)).issues.toList();

if (code.text.trim().isEmpty) {
return fce.AnalysisResult(issues: issues);
}

try {
jsonDecode(code.text);
} on FormatException catch (error) {
// ISSUE-6312: Translate JSON parsing failures into gutter-visible issues.
issues.add(
fce.Issue(
line: _lineFromOffset(code.text, error.offset),
message: error.message,
type: fce.IssueType.error,
),
);
}

return fce.AnalysisResult(issues: issues);
}

int _lineFromOffset(String text, int? offset) {
// ISSUE-6312: Map the parser offset back to a line number for gutter
// rendering.
final safeOffset = (offset ?? 0).clamp(0, text.length);
return '\n'.allMatches(text.substring(0, safeOffset)).length;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import 'package:flutter_code_editor/flutter_code_editor.dart' as fce;
import 'package:flutter_test/flutter_test.dart';
import 'package:highlight/languages/json.dart';

import 'package:flet_code_editor/src/utils/flet_code_controller.dart';
import 'package:flet_code_editor/src/utils/json_analyzer.dart';

void main() {
// ISSUE-6312: Regression coverage for missing JSON gutter error markers.
group('FletCodeController JSON analyzer', () {
test('uses JSON analyzer for JSON language', () {
final controller = FletCodeController(
text: '{"name": "flet"}',
language: json,
);

expect(controller.analyzer, isA<JsonLocalAnalyzer>());
});

test('reports invalid JSON syntax as gutter issues', () async {
final controller = FletCodeController(
text: '{\n "name": "flet"\n "version": 1\n}',
language: json,
);

await controller.analyzeCode();

expect(controller.analysisResult.issues, hasLength(1));
expect(controller.analysisResult.issues.single.line, 2);
expect(controller.analysisResult.issues.single.type, fce.IssueType.error);
});

test('keeps valid JSON free of issues', () async {
final controller = FletCodeController(
text: '{\n "name": "flet",\n "version": 1\n}',
language: json,
);

await controller.analyzeCode();

expect(controller.analysisResult.issues, isEmpty);
});
});
}