{"record":{"id":"846adc849b3924c5","repo":"oxc-project/oxc","slug":"expected-a-function-style","errorCode":null,"errorMessage":"Expected a function {style}.","messagePattern":"Expected a function (.+?)\\.","errorType":"validation","errorClass":"OxcDiagnostic","httpStatus":null,"severity":"warning","filePath":"crates/oxc_linter/src/rules/eslint/func_style.rs","lineNumber":22,"sourceCode":"\nuse oxc_ast::{\n    AstKind,\n    ast::{ArrowFunctionExpression, Function, FunctionType, Super, ThisExpression},\n};\nuse oxc_ast_visit::VisitJs;\nuse oxc_diagnostics::OxcDiagnostic;\nuse oxc_macros::declare_oxc_lint;\nuse oxc_semantic::{AstNode, ScopeFlags};\nuse oxc_span::Span;\n\nuse crate::{\n    ast_util::nth_outermost_paren_parent,\n    context::LintContext,\n    rule::{Rule, TupleRuleConfig},\n};\n\nfn func_style_diagnostic(span: Span, style: &str) -> OxcDiagnostic {\n    OxcDiagnostic::warn(format!(\"Expected a function {style}.\"))\n        .with_help(\"Enforce the consistent use of either `function` declarations or expressions assigned to variables\")\n        .with_label(span)\n}\n\n#[derive(Debug, Default, PartialEq, Clone, Copy, Deserialize, Serialize, JsonSchema)]\n#[serde(rename_all = \"camelCase\")]\nenum Style {\n    #[default]\n    Expression,\n    Declaration,\n}\n\nimpl Style {\n    pub fn as_str(&self) -> &str {\n        match self {\n            Style::Expression => \"expression\",\n            Style::Declaration => \"declaration\",\n        }","sourceCodeStart":4,"sourceCodeEnd":40,"githubUrl":"https://github.com/oxc-project/oxc/blob/e1e7af627c8843ab64044ed466b128fcc21a035b/crates/oxc_linter/src/rules/eslint/func_style.rs#L4-L40","documentation":"Oxlint's port of the ESLint rule func-style: it forces one definition style per codebase. The Style enum (camelCase serde over kebab-case values) is `expression` (the default) or `declaration` (crates/oxc_linter/src/rules/eslint/func_style.rs:20). Under `expression`, top-level `function foo() {}` declarations are reported with 'Expected a function expression.'; under `declaration`, `const foo = function () {}` assignments are reported with 'Expected a function declaration.'.","triggerScenarios":"Config [\"warn\", \"expression\"] plus a `function helper() {}` declaration; config [\"warn\", \"declaration\"] plus a `const helper = function () {}` assignment.","commonSituations":"Standardizing a codebase that grew with mixed styles; hoisting-dependent code that actually requires declarations; formatter rewrites that do not change the underlying style.","solutions":["Convert the flagged function to the enforced style (expression: const + function/arrow; declaration: `function name()`).","Choose the option matching the majority of the codebase to minimize churn.","Disable the rule if the team accepts both styles.","Watch for hoisting: if the function is used before its definition point, a declaration is required."],"exampleFix":"// before (style: expression)\nfunction helper(x) {\n  return x * 2;\n}\n\n// after\nconst helper = (x) => x * 2;","handlingStrategy":"validation","validationCode":"// .oxlintrc.json — pick the dominant style of the codebase\n{\n  \"rules\": {\n    \"func-style\": [\"warn\", \"expression\"]\n  }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Settle one style in the shared config before scaling the team.","Use declarations when hoisting is required (calls before definition in module scope).","Do not fight the rule with per-file disables; change the config instead."],"tags":["eslint","oxlint","style","function-declaration","function-expression"],"backgroundTag":"function-declaration-style","analyzedSha":"e1e7af627c8843ab64044ed466b128fcc21a035b","analyzedAt":"2026-08-20T07:01:07.079Z","contentChangedAt":"2026-08-20T07:01:07.079Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}