Annotation Reference
Entity Annotations
@QfEntity
Declares a class as a Q-Framework entity. Placed on the domain entity class.
@QfEntity(
appKey = "app",
name = @QfI18n(
defaultMessage = "Product",
texts = { @QfI18nText(locale = "ko", message = "상품") }
),
autoHistoryEnabled = false,
deletePolicy = @QfCrudPolicy(enabled = true),
capabilityKey = "product-management"
)
public class ProductEntity { }| Attribute | Type | Description | Default |
|---|---|---|---|
appKey | String | Owning client app key | "" (uses declared app) |
name | @QfI18n | Localized display name | @QfI18n(texts = {}) |
autoHistoryEnabled | boolean | Enable automatic change history | false |
deletePolicy | @QfCrudPolicy | Delete operation policy | @QfCrudPolicy(enabled = false) |
treePolicy | @QfTreePolicy | Tree/hierarchical structure config | @QfTreePolicy (disabled) |
ownerPolicy | @QfOwnerPolicy | Ownership and visibility policy (org or user) | @QfOwnerPolicy(enabled = false) |
masterRelation | @QfMasterRelation | Master-detail relationship | @QfMasterRelation(enabled = false) |
capabilityKey | String | Linked capability key | "" (derived from class name) |
excelDownloadable | boolean | Enable Excel export endpoint | true |
excelUploadable | boolean | Enable Excel import endpoint | true |
displayTextRules | @QfComposedText[] | Rules for composing display text from multiple fields | {} |
requireSearchTrigger | boolean | Require explicit search action before loading data | false |
hideRowNumber | boolean | Hide the row number column | false |
autoSelectSingleResult | boolean | Automatically select when query returns exactly one result | false |
forceRowSelection | boolean | Require row selection before entity-level actions | false |
masterEntityDependentMode | QfMasterEntityDependentMode | DEPENDENT: framework validates that a master entity exists as a structural reference of this entity type. INDEPENDENT: no such validation. | DEPENDENT |
buttons | @QfButton[] | Entity-level action buttons | {} |
exposeOn | @QfExposeOn[] | App/capability exposure rules | {} |
managementConditions | @QfConditionExpr[] | Additional conditions applied to the management view | {} |
excludedApiTypes | QfGeneratedApiTypeEnum[] | API endpoint types to exclude from code generation | {} |
apiGenerationGroup | QfGeneratedApiTypeGroupEnum | API generation group | all |
QfGeneratedApiTypeEnum values
| Value | Description |
|---|---|
create | Create a new entity record |
list | Paged/filtered list of records |
detail | Single record by key/conditions |
load_update | Load initial data for update screens |
update | Modify an existing record |
delete | Remove a record (soft or hard depending on policy) |
histories | Change history / audit records |
unique | Check uniqueness of an attribute value |
order | Update ordering/sort sequence |
tree | Hierarchical entity data as a tree |
key_value | Simplified key-value dataset (selectors, code tables) |
update_key_value | Update key-value style configuration records |
excel_create | Register an Excel upload/download job |
excel_process | Parse/validate/apply uploaded Excel data |
excel_download | Export data to an Excel file |
excel_sample_download | Download an Excel template for upload |
excel_download_poll | Poll asynchronous Excel download progress |
excel_download_cancel | Cancel an asynchronous Excel download job |
excel_process_poll | Poll asynchronous Excel processing progress |
excel_process_cancel | Cancel an asynchronous Excel processing job |
excel_download_result | Return downloadable result once a job finishes |
asyncsearch | Run a potentially slow search as an asynchronous job |
QfGeneratedApiTypeGroupEnum values
| Value | Generated APIs | Description |
|---|---|---|
all | All types | Generate all supported API types (no exclusions) |
only_crud | CRUD + query APIs | Excludes Excel workflow APIs and asyncsearch |
excel | Excel workflow APIs | Excludes general CRUD/query and other non-Excel utilities |
only_read | list, detail | Generates list and detail only |
only_list | list | Generates list only |
@QfClientApp
Declares a client application. Placed on a configuration class.
@QfClientApp(
key = "app",
name = @QfI18n(
defaultMessage = "App",
texts = { @QfI18nText(locale = "ko", message = "일반 앱") }
)
)
public class AppConfig { }| Attribute | Type | Required | Description |
|---|---|---|---|
key | String | ✅ | Unique client app key |
name | @QfI18n | Localized display name | |
description | String | Brief description of the app | |
order | int | Display order hint (lower = first) |
Capability / Permission Annotations
@QfCapability
Declares a business function area (Capability). Placed on a dedicated class.
@QfCapability(
key = "product-management",
name = @QfI18n(defaultMessage = "Product Management", texts = {}),
entities = { ProductEntity.class },
privileges = {
@QfPrivilege(key = "product-management__create"),
@QfPrivilege(key = "product-management__delete")
}
)
public final class ProductManagementCapability { }| Attribute | Type | Required | Description |
|---|---|---|---|
key | String | ✅ | Unique capability key |
name | @QfI18n | Localized display name | |
entities | Class[] | Primary managed entity classes | |
privileges | @QfPrivilege[] | Privileges defined by this capability |
Entities are linked to a capability via @QfEntity(capabilityKey = "..."), not by placing @QfCapability on the entity class.
@QfPrivilege
Declares a permission unit within a @QfCapability.
@QfPrivilege(
key = "product-management__create",
name = @QfI18n(defaultMessage = "Create Product", texts = {})
)| Attribute | Type | Required | Description |
|---|---|---|---|
key | String | ✅ | Unique key (scoped within Capability) |
name | @QfI18n | Localized display name |
Security Annotations
@QfCrypto
Automatically encrypts and decrypts a field. Placed on a field.
@QfCrypto
private String email;
@QfCrypto(algorithm = QfCrypto.CryptoAlgorithm.bcrypt)
private String password;Restriction
Cannot be combined with @QfSearch (compile error).
| Attribute | Type | Description | Default |
|---|---|---|---|
algorithm | CryptoAlgorithm | Persistence algorithm | aes256 |
CryptoAlgorithm values
| Value | Direction | Description |
|---|---|---|
aes256 | Symmetric (reversible) | AES-256 encryption |
sha256 | One-way | SHA-256 hash |
pbkdf2 | One-way | PBKDF2 key derivation |
bcrypt | One-way | BCrypt password hash |
argon2 | One-way | Argon2 password hash / KDF |
rsaCipher | Asymmetric (reversible) | RSA encryption |
rsaKey | — | RSA key material storage |
rsaSignature | — | RSA signature |
@QfOwnerPolicy (element)
Declares the data ownership and visibility policy for an entity. Supports two ownership models:
ORGANIZATION— data is owned by an organization; filtered by org hierarchy traversalUSER— data is owned by a user; filtered byprincipalIdequality
Used as an element inside @QfEntity:
// Organization ownership — own org only (default)
@QfEntity(
ownerPolicy = @QfOwnerPolicy(enabled = true, attribute = "orgId")
)
// Organization ownership — own org + all descendants
@QfEntity(
ownerPolicy = @QfOwnerPolicy(
enabled = true,
attribute = "orgId",
include = QfOrganizationInclude.ANCHOR_AND_DESCENDANTS
)
)
// User ownership — only the creator can see their own data
@QfEntity(
ownerPolicy = @QfOwnerPolicy(
enabled = true,
ownerType = QfOwnerType.USER,
attribute = "createdBy"
)
)| Attribute | Type | Description | Default |
|---|---|---|---|
enabled | boolean | Enable ownership filtering | true |
ownerType | QfOwnerType | ORGANIZATION or USER | ORGANIZATION |
attribute | String | Field name holding the owner ID | "" |
anchorKind | QfOrganizationAnchorKind | Anchor strategy (ORGANIZATION only) | SELF |
anchorDepth | int | Anchor depth (ORGANIZATION only) | 0 |
include | QfOrganizationInclude | Traversal direction (ORGANIZATION only) | ANCHOR_ONLY |
maxAncestorDepth | int | Max ancestor levels, -1 = unlimited | -1 |
maxDescendantDepth | int | Max descendant levels, -1 = unlimited | -1 |
overrideMode | QfOrganizationPolicyOverrideMode | Global policy override behavior | REPLACE |
QfOrganizationAnchorKind values
| Value | Description |
|---|---|
ROOT | Use the root (top-most) organization as the anchor |
SELF | Use the current organization as the anchor (default) |
ANCESTOR_RELATIVE_DEPTH | Use the ancestor at the given relative depth (0 = self, 1 = parent, …) |
ANCESTOR_ABSOLUTE_DEPTH | Use the ancestor whose absolute depth from root matches anchorDepth |
QfOrganizationInclude values
| Value | Description |
|---|---|
ANCHOR_ONLY | Include only the anchor organization (default) |
ANCHOR_AND_DESCENDANTS | Include anchor and all descendant organizations |
ANCHOR_AND_ANCESTORS | Include anchor and all ancestor organizations |
ANCHOR_AND_ANCESTORS_AND_DESCENDANTS | Include anchor, all ancestors, and all descendants |
CUSTOM | Custom traversal strategy (application-defined) |
QfOrganizationPolicyOverrideMode values
| Value | Description |
|---|---|
REPLACE | Entity policy completely replaces the global policy (default) |
RESTRICT | Entity policy may only narrow the global policy (prevents accidental privilege widening) |
Validation Annotations
@QfValidationRule
Declares a validation rule on a field. Repeatable.
@QfValidationRule(
rule = QfValidationRule.Rule.regex,
params = {"^[A-Za-z0-9_]+$"},
invalidValueMessageKey = "validation.loginId.invalid"
)
private String loginId;| Attribute | Type | Required | Description |
|---|---|---|---|
rule | Rule | ✅ | Validation rule type |
params | String[] | Rule parameters (pattern for regex) | |
invalidValueMessageKey | String | Error message resource key (mutually exclusive with invalidValueMessages) | |
invalidValueMessages | @QfI18n | Inline error message (mutually exclusive with invalidValueMessageKey) | |
serverOnly | boolean | Server-side only validation | |
applyOn | @QfConditionExpr[] | Conditions for rule application | |
references | @QfValidationRuleReference[] | Cross-attribute references for validation (e.g., password confirmation, date comparison) |
Mutually exclusive
invalidValueMessageKey and invalidValueMessages are mutually exclusive. Use invalidValueMessageKey when the message is defined in a message resource file, and invalidValueMessages for inline messages.
Rule enum values:
| Rule | Description | params |
|---|---|---|
regex | Custom regex | params[0] = pattern |
unique | Server uniqueness check | params[0] = URL (optional) |
login_id | Login ID format (from config) | — |
user_pwd | Password policy (from config) | — |
Display Annotations
@QfListAttribute
Displays as a column in the list view.
@QfListAttribute(sortable = true)
private String name;| Attribute | Type | Default | Description |
|---|---|---|---|
sortable | boolean | false | Whether sortable |
cannotHide | boolean | false | Prevent user from hiding column |
order | int | 0 | Column display order (lower = earlier) |
uiClasses | @QfUiClasses[] | {} | UI class definitions for this column |
subattributes | Subattribute[] | {} | Sub-lines from an entity-typed attribute |
showOn | @QfConditionExpr[] | {} | Conditional visibility expressions |
buttons | @QfButton[] | {} | Row-level action buttons |
exposeOn | @QfExposeOn[] | {} | App/capability visibility rules |
@QfListAttribute.Subattribute inner annotation
Used inside subattributes to declare which inner attributes of an entity-typed field should be rendered as sub-lines in the list cell.
@QfListAttribute(
subattributes = {
@QfListAttribute.Subattribute(attributeName = "code"),
@QfListAttribute.Subattribute(attributeName = "name")
}
)
private CategoryEntity category;| Attribute | Type | Description | Default |
|---|---|---|---|
attributeName | String | Inner attribute name to render | (required) |
name | @QfI18n | Localized subattribute label | @QfI18n(texts = {}) |
displayTextRules | @QfComposedText[] | Rules for composing display text | {} |
controlType | QfControlType.Type | Rendering control type | text |
@QfDetailAttribute
Displays in the detail view.
@QfDetailAttribute
private String name;| Attribute | Type | Description | Default |
|---|---|---|---|
uiClasses | @QfUiClasses[] | UI class definitions | {} |
exposeOn | @QfExposeOn[] | App/capability visibility rules | {} |
showOn | @QfConditionExpr[] | Visibility conditions | {} |
order | int | Display order (lower = earlier) | 0 |
@QfCreateAttribute
Displays as an input field in the create form.
@QfCreateAttribute(
requiredOn = @QfRequiredOn(always = true)
)
private String name;| Attribute | Type | Description | Default |
|---|---|---|---|
exposeOn | @QfExposeOn[] | App/capability visibility rules | {} |
requiredOn | @QfRequiredOn | Required rule | @QfRequiredOn |
readonlyOn | @QfReadonlyOn | Read-only rule | @QfReadonlyOn |
initialValue | String | Static initial value | "" |
dynamicInitialValue | @QfComposedText[] | Dynamic initial value (takes precedence over initialValue) | {} |
uiClasses | @QfUiClasses[] | UI class definitions | {} |
showOn | @QfConditionExpr[] | Visibility conditions | {} |
disableOn | @QfConditionExpr[] | Disable conditions | {} |
syncValueFrom | String | Copy value from another attribute path | "" |
initialValues | InitialValue[] | Nested initial values for entity-type attributes | {} |
setValuesFrom | String[] | Attribute names whose last-entered values carry forward as defaults | {} |
@QfUpdateAttribute
Displays as an input field in the update form.
@QfUpdateAttribute(
requiredOn = @QfRequiredOn(always = true)
)
private String name;| Attribute | Type | Description | Default |
|---|---|---|---|
exposeOn | @QfExposeOn[] | App/capability visibility rules | {} |
requiredOn | @QfRequiredOn | Required rule | @QfRequiredOn |
readonlyOn | @QfReadonlyOn | Read-only rule | @QfReadonlyOn |
uiClasses | @QfUiClasses[] | UI class definitions | {} |
showOn | @QfConditionExpr[] | Visibility conditions | {} |
disableOn | @QfConditionExpr[] | Disable conditions | {} |
syncValueFrom | String | Copy value from another attribute path | "" |
order | int | Column display order (lower = earlier) | 0 |
TIP
@QfUpdateAttribute does not have initialValue / dynamicInitialValue parameters — those are specific to @QfCreateAttribute.
@QfSearch
Enables the field as a search filter in the list view.
@QfSearch(type = QfSearch.Type.text)
private String name;
@QfSearch(type = QfSearch.Type.select)
private String status;| Attribute | Type | Description | Default |
|---|---|---|---|
type | Type | Search control type | auto |
exposeOn | @QfExposeOn[] | App/capability visibility rules | {} |
showOn | @QfConditionExpr[] | Visibility conditions | {} |
caseSensitive | CaseSensitive | Case sensitivity (sensitive/insensitive) | insensitive |
condition | Condition | Match condition (like/exact) | like |
conditions | @QfConditionExpr[] | Additional conditions applied to option/search data | {} |
target | String | Association path to the effective search target (e.g. "invcNo.hdry") | "" |
multiple | QfControlType.MultipleValue | Multi-value policy | unset |
Type enum values
| Type | Description |
|---|---|
auto | Auto-detect based on field type |
text | Plain text input |
select | Single-select dropdown |
true_or_false | Boolean toggle |
multiselect | Multi-select |
period_date | Date range |
period_datetime | Datetime range |
Auto-resolution rules (type = auto)
- Primitive / wrapper /
String→text String+@QfCodeGroup→select- User-defined class →
select
When resolved to select, caseSensitive is forced to sensitive and condition is forced to exact.
@QfOptions
Declares option metadata for choice-based controls (select, multiselect, radio, etc.).
By default, for code-based or entity-typed attributes, options are resolved automatically. Use @QfOptions to override the default resolution, apply additional conditions, or define fully manual options.
@QfOptions(
conditions = {
@QfConditionExpr({
@QfCondToken(type = QfCondTokenType.ATOM,
atom = @QfCondition(attributeName = "alias", notIn = {"user_status.system"}))
})
}
)
private UserStatus status;| Attribute | Type | Description | Default |
|---|---|---|---|
conditions | @QfConditionExpr[] | Conditions for filtering option candidates | {} |
optionModel | @QfOptionModel | Explicit option model (entity or code group) | @QfOptionModel |
name | String | Attribute on the relation model that references the current entity | "" |
referencedAttributeName | String | Attribute on the current entity that joins to the relation model key | "" |
searchAttributeName | String | Target attribute in the relation model used as the search attribute | "" |
displayTextRules | @QfComposedText[] | Rules for composing option labels | {} |
asyncSearch | @QfAsyncSearch | Async search configuration (for large or dynamic option sets) | @QfAsyncSearch |
customOptions | @QfCustomOption[] | Fully manual option list (takes precedence over all other settings when non-empty) | {} |
Custom options take full precedence
When customOptions is non-empty, all other @QfOptions settings (conditions, optionModel, asyncSearch, etc.) are ignored.
@QfOptionModel parameters
| Attribute | Type | Description | Default |
|---|---|---|---|
codeGroup | String | Code group identifier when the option model is backed by a code table | "" |
condition | String | Additional filter condition for option lookup (e.g., JPQL fragment) | "" |
@QfAsyncSearch parameters
| Attribute | Type | Description | Default |
|---|---|---|---|
watch | String | Attribute to watch; if empty, uses the current attribute's typed input | "" |
target | String[] | Attribute names in the option model to search/match against | {} |
url | String | Custom API endpoint for async option resolution | "" |
@QfCustomOption parameters
| Attribute | Type | Description | Default |
|---|---|---|---|
names | @QfI18n | Localized display name of the option | (required) |
value | String | Actual option value to submit/store | (required) |
@QfComposedText (element)
Declares display text composition rules. Repeatable — multiple @QfComposedText entries are processed in declaration order.
| Attribute | Type | Description | Default |
|---|---|---|---|
segments | @QfTextSegment[] | Parts used to compose the display text, concatenated in order | (required) |
useI18n | boolean | If true, treats the composed string as a message key and resolves it via i18n lookup | false |
@QfCrudPolicy (element)
Declares a CRUD operation policy. Used as an element inside @QfEntity (e.g., deletePolicy = @QfCrudPolicy(...)).
| Attribute | Type | Description | Default |
|---|---|---|---|
enabled | boolean | Whether the operation is enabled | true |
forbiddenTooltip | String | Tooltip message key shown when the operation is forbidden | "" |
conditions | @QfConditionExpr[] | Conditional constraints evaluated against runtime context | {} |
@QfControlType
Declares the UI control type for a field.
@QfControlType(QfControlType.Type.email)
private String email;
@QfControlType(QfControlType.Type.textarea)
private String description;
@QfControlType(value = QfControlType.Type.number, minValue = 0, maxValue = 100)
private Integer score;| Attribute | Type | Description | Default |
|---|---|---|---|
value | Type | Control type | (required) |
hint | @QfI18n | Placeholder / help text | @QfI18n(texts = {}) |
multiple | MultipleValue | Multi-value policy (multiple/single/unset) | unset |
regex | String | Regex for random_string type | "" |
minValue | long | Minimum value (number type) | Long.MIN_VALUE |
maxValue | long | Maximum value (number type) | Long.MAX_VALUE |
uniqueOn | String | Uniqueness key attribute within section_list | "" |
passwordConfirm | boolean | Request confirmation input (password type) | false |
Type enum values
| Value | Description |
|---|---|
text | Plain text input |
display | Display-only (read-only) |
random_string | Auto-generated random string (uses regex) |
password | Password input |
textarea | Multi-line text area |
html_editor | Rich text (HTML) editor |
select | Single-select |
multiselect | Multi-select |
file | File upload |
number | Numeric input |
i18n | Internationalized text |
weekday | Single weekday selection |
weekdays | Multiple weekday selection |
icon | Icon selector |
date | Date picker |
time | Time picker |
datetime | Datetime picker |
date_simple_string | Date as plain string (e.g. yyyyMMdd) |
time_simple_string | Time as plain string (e.g. HHmm) |
tel | Telephone number |
email | Email address |
point | Coordinates (lat/lng) |
zip | Postal code |
checkbox | Checkbox |
section | Layout section separator |
section_list | Repeatable section list |
map | Map / location control |
radio | Radio button group |
paint | Drawing area |
hidden | Hidden field (has value, not displayed) |
Button Annotations
@QfButton
Declares a button rendered inside a list column or entity toolbar. Used as element of @QfListAttribute(buttons = ...) or @QfEntity(buttons = ...).
@QfListAttribute(
buttons = {
@QfButton(
frontendComponent = "ProductDetailModal",
name = @QfI18n(defaultMessage = "Detail"),
icon = "cilInfo",
color = "primary",
size = "xl"
)
}
)| Attribute | Type | Description | Default |
|---|---|---|---|
frontendComponent | String | Frontend component rendered inside the modal | (required) |
name | @QfI18n | Localized button label | @QfI18n(defaultMessage = "button", texts = {}) |
icon | String | Icon identifier (CoreUI) | "" |
color | String | Button color (CoreUI) | "secondary" |
size | String | Modal size (sm / lg / xl / full) | "xl" |
actionType | ActionType | Click action type (MODAL / NONE) | MODAL |
enabledOnChecked | boolean | Enable only when at least one row is checked | false |
modalCloseOnly | boolean | Modal shows only a close button (no confirm) | false |
inputs | Input[] | Input fields rendered inside the modal | {} |
conditions | @QfConditionExpr[] | Visibility conditions for the button | {} |
displayTextRules | @QfComposedText[] | Rules for composing display text | {} |
@QfButton.Input parameters
| Attribute | Type | Description | Default |
|---|---|---|---|
key | String | Input parameter identifier | (required) |
type | String | Input type (e.g. text, number) | (required) |
placeholder | @QfI18n | Localized placeholder text | @QfI18n(texts = {}) |
Structural Annotations
@QfMasterRelation (element)
Declares a master-detail relationship. Used as an element inside @QfEntity:
@QfEntity(
masterRelation = @QfMasterRelation(
enabled = true,
masterEntityFqcn = "com.example.OrderEntity",
masterKeyAttribute = "orderId",
onMasterDelete = QfMasterRelation.OnMasterDelete.CASCADE_DELETE
)
)
public class OrderItemEntity { }| Attribute | Type | Description | Default |
|---|---|---|---|
enabled | boolean | Enable the master relation | false |
masterEntityFqcn | String | Fully-qualified class name of the master entity | "" |
masterKeyAttribute | String | Attribute on this entity that holds the master's ID | "" |
onMasterDelete | OnMasterDelete | Cascade policy when master is deleted | IGNORE |
onMasterDelete | Description |
|---|---|
CASCADE_DELETE | Delete details when master is deleted |
RESTRICT | Reject master deletion if details exist |
IGNORE | Leave details orphaned |
@QfTreePolicy (element)
Declares tree behavior policy. Used as an element inside @QfEntity:
@QfEntity(
treePolicy = @QfTreePolicy(editableRoot = true, draggable = false)
)
public class CategoryEntity { }| Attribute | Type | Description | Default |
|---|---|---|---|
editableRoot | boolean | Whether the root node of the current tree view is editable | false |
draggable | boolean | Enable drag-and-drop reordering | true |
@QfParent / @QfTreeDepth / @QfChildren
Declare tree structure fields.
@QfParent
private String parentId;
@QfTreeDepth
private Integer depth;
@QfChildren
private List<CategoryEntity> children;@QfParent parameters
| Attribute | Type | Description | Default |
|---|---|---|---|
defaultValue | String | Sentinel value representing a root node (no parent) | "" |
defaultNull | boolean | Whether root nodes use null as the parent value | false |
@QfTreeDepth parameters
| Attribute | Type | Description | Default |
|---|---|---|---|
defaultValue | int | Default depth value (1 = root) | 1 |
@QfGroup
Groups related fields together in the UI.
@QfGroup(alias = "address_info")
private String address;
@QfGroup(alias = "address_info")
private String zipCode;| Attribute | Type | Description | Default |
|---|---|---|---|
alias | String | Group identifier (stable key for templates and UI rendering) | (required) |
name | @QfI18n | Localized group label | @QfI18n(defaultMessage = "group", texts = {}) |
uiClasses | @QfUiClasses[] | UI class definitions applied to the group | {} |
Lifecycle Hook Annotations
@QfOn
Declares a hook method to be called at a specific point in the CRUD pipeline. Repeatable.
@QfOn(phase = QfOnPhase.BEFORE, op = QfOnOp.CREATE)
public void beforeCreate(QfPipelineContext ctx) { ... }
@QfOn(phase = QfOnPhase.AFTER, op = QfOnOp.UPDATE, when = QfOnWhen.SUCCESS)
public void afterUpdate(QfPipelineContext ctx) { ... }| Attribute | Type | Description | Default |
|---|---|---|---|
phase | QfOnPhase | Execution phase | (required) |
op | QfOnOp | Target operation | (required) |
layer | QfOnLayer | Execution layer | DOMAIN |
io | QfOnIo | I/O type | NONE |
scope | QfOnScope | Data scope | SINGLE |
when | QfOnWhen | Execution condition (AFTER phase) | ALWAYS |
order | int | Execution order among hooks at the same point | 0 |
QfOnPhase
| Value | Description |
|---|---|
BEFORE | Executed before the operation |
AFTER | Executed after the operation |
QfOnOp
| Value | Description |
|---|---|
CREATE | Create operation |
READ | Read (single record) |
UPDATE | Update operation |
DELETE | Delete operation |
LIST | List/query operation |
DETAIL | Detail view |
TREE | Tree query |
EXPORT | Data export (Excel/CSV) |
IMPORT | Data import (Excel/CSV) |
SEARCH | Search/filter |
UNIQUE_SEARCH | Uniqueness check search |
MASTER_ENTITY | Master entity lookup |
QfOnLayer
| Value | Description |
|---|---|
REQUEST | Request boundary (before/after API endpoint) |
DOMAIN | Domain/service processing (default) |
COMMIT | After transaction commit |
QfOnScope
| Value | Description |
|---|---|
SINGLE | Single record (default) |
LIST | Collection of records |
BULK | Bulk operation |
QfOnWhen (meaningful in AFTER phase)
| Value | Description |
|---|---|
ALWAYS | Always execute (default) |
SUCCESS | Only on successful execution |
FAILURE | Only on failed execution |
QfOnIo
| Value | Description |
|---|---|
NONE | No special I/O (default) |
EXCEL | Excel import/export |
CSV | CSV import/export |
Audit Trail Annotations
Auto-populated by the framework at write time:
| Annotation | Description |
|---|---|
@QfRgsOperId | Records the creator's user ID |
@QfRgsOperDt | Records the creation timestamp |
@QfRgsOperIp | Records the creator's IP address |
@QfUpdtOperId | Records the last updater's user ID |
@QfUpdtOperDt | Records the last update timestamp |
@QfUpdtOperIp | Records the updater's IP address |
@QfDeleteOperId | Records the deleter's user ID |
@QfDeleteOperDt | Records the deletion timestamp |
@QfDeleteOperIp | Records the deleter's IP address |
@QfDeleteFlag | Marks the record as soft-deleted |
@QfDeleteFlag parameters
| Attribute | Type | Description | Default |
|---|---|---|---|
deletedValues | String[] | Values that represent the deleted state (e.g. {"Y"}, {"1"}, {"true"}) | {} |
valueType | QfDeleteValueType | Forces the comparison type for the flag value | AUTO |
valueType | Description |
|---|---|
AUTO | Auto-detect based on attribute type |
STRING | String-based comparison |
BOOLEAN | Boolean-based comparison |
INTEGER | Integer-based comparison |
LONG | Long-based comparison |
Result Code Annotations
@QfResultCode
Declares a result code. Placed on a type.
@QfResultCode(
code = "Q-MY-APP-000001",
messageKey = "result_code.text.q_my_app_000001",
cause = "Product not found",
resolution = "Check the product ID and retry.",
target = "Product"
)
public interface ProductResultCode { }| Attribute | Type | Description | Default |
|---|---|---|---|
code | String | Globally unique result code (e.g. Q-MY-APP-000001) | (required) |
cause | String | Short developer-facing description of the cause | (required) |
resolution | String | Actionable guidance to resolve or handle the situation | (required) |
target | String | Primary applicable target (module/component/handler) | (required) |
messageKey | String | Message resource key (auto-generated if empty) | "" |
For details, see the Result Code Reference.
Internationalization Annotations
@QfI18n
Declares a localized message bundle. Used as an element inside other annotations.
@QfI18n(
defaultMessage = "Product Name",
texts = {
@QfI18nText(locale = "ko", message = "상품명"),
@QfI18nText(locale = "ja", message = "商品名")
},
key = "entity.product.name.label", // optional; auto-generated if empty
sync = false
)| Attribute | Type | Default | Description |
|---|---|---|---|
defaultMessage | String | "" | Fallback text when no locale matches |
texts | @QfI18nText[] | {} | Locale-specific messages |
key | String | "" | Message lookup key (auto-generated if empty) |
sync | boolean | false | Sync with source on every startup |
@QfI18nText
One locale-specific message within a @QfI18n bundle.
@QfI18nText(locale = "ko", message = "상품명")| Attribute | Type | Description | Default |
|---|---|---|---|
locale | String | Locale identifier (e.g. ko, en) | (required) |
message | String | Localized message text | (required) |
sync | boolean | Force-sync this locale entry on every startup | false |
Enum Reference
QfMenuDisplayLocationEnum
Defines where a menu item is rendered in the client UI. Used by the framework to normalize menu placement across different frontend implementations.
| Value | Description |
|---|---|
main | Primary navigation area |
top | Top / header bar |
bottom | Bottom / footer bar |
left | Secondary left-side area |
right | Secondary right-side area |
@QfDisplayHint
Declares a hint (tooltip / placeholder) for a field.
@QfDisplayHint(text = "Enter the product name")
private String name;
@QfDisplayHint(key = "hint.product.name") // resolved from message resource
private String name;| Attribute | Type | Description | Default |
|---|---|---|---|
key | String | Message resource key for i18n resolution | "" |
text | String | Literal hint text (fallback when key is not set or cannot be resolved) | "" |
Sorting & Data Annotations
@QfOrder
Marks an attribute as the default sort key for list queries.
@QfOrder(direction = QfOrder.Direction.desc)
private LocalDateTime createdAt;| Attribute | Type | Description | Default |
|---|---|---|---|
direction | Direction | Sort direction | asc |
Direction values: asc, desc
@QfSeparator
Declares a custom delimiter for serializing collection-type attributes.
@QfSeparator("|")
private List<String> tags;| Attribute | Type | Description | Default |
|---|---|---|---|
value | String | Delimiter used to join collection elements | (required) |
@QfCodeGroup
Marks an attribute as a code-based attribute resolved from a code table.
@QfCodeGroup(alias = "STATUS_CODE")
private String status;| Attribute | Type | Description | Default |
|---|---|---|---|
alias | String | Code group identifier | (required) |
Structural Data Annotations
@QfEmbeddedId
Marks an attribute as a composite/embedded identifier. No parameters.
@QfEmbeddedId
private OrderId id;@QfMap
Declares a virtual map (location) attribute rendered as a map widget. The actual data is stored in separate address/coordinate attributes.
@QfMap(
addressAttributeName = "address",
latitudeAttributeName = "lat",
longitudeAttributeName = "lng"
)
private Object location;| Attribute | Type | Description | Default |
|---|---|---|---|
addressAttributeName | String | Attribute name that stores the address | (required) |
latitudeAttributeName | String | Attribute name that stores the latitude | (required) |
longitudeAttributeName | String | Attribute name that stores the longitude | (required) |
Conditional Behavior Annotations
@QfForceTransfer
Forces an attribute to always be included in the transfer payload, even if it is not exposed as a list/create/update/detail attribute.
@QfForceTransfer
private String internalCode;| Attribute | Type | Description | Default |
|---|---|---|---|
exposeOn | @QfExposeOn[] | Per-app/capability exposure rules | {} |
conditions | @QfConditionExpr[] | Conditions under which force-transfer applies | {} |
@QfRequiredOn (element)
Declares when an attribute is required. Used as a nested element in @QfCreateAttribute / @QfUpdateAttribute.
| Attribute | Type | Description | Default |
|---|---|---|---|
always | boolean | Always required (conditions must be empty) | false |
conditions | @QfConditionExpr[] | Conditions that make the attribute required | {} |
@QfReadonlyOn (element)
Declares when an attribute is read-only. Used as a nested element in @QfCreateAttribute / @QfUpdateAttribute.
| Attribute | Type | Description | Default |
|---|---|---|---|
always | boolean | Always read-only (conditions must be empty) | false |
conditions | @QfConditionExpr[] | Conditions that make the attribute read-only | {} |
@QfExposeOn (element)
Declares per-app/capability visibility rules. Used as a nested element in attribute annotations.
| Attribute | Type | Description | Default |
|---|---|---|---|
appKeys | String[] | Client app keys where this element is exposed (empty = all apps) | {} |
capabilities | String[] | Capability aliases where this element is exposed (empty = all capabilities) | {} |
@QfUiClasses
Declares UI class names applied to an attribute, with optional conditions. Repeatable.
@QfUiClasses(value = {"text-danger", "fw-bold"})
private String status;| Attribute | Type | Description | Default |
|---|---|---|---|
value | String[] | CSS/UI class names to apply | {} |
exposeOn | @QfExposeOn[] | Per-app/capability exposure rules | {} |
conditions | @QfConditionExpr[] | Conditions under which the classes are applied | {} |
Condition Annotations
Condition annotations compose predicates used in conditions, showOn, disableOn, etc.
@QfConditionExpr
A condition expression defined as a flat token stream.
// A == "Y" AND (B IS NOT EMPTY OR C != "N")
@QfConditionExpr({
@QfCondToken(type = QfCondTokenType.ATOM, atom = @QfCondition(attributeName = "a", equal = "Y")),
@QfCondToken(type = QfCondTokenType.AND),
@QfCondToken(type = QfCondTokenType.LPAREN),
@QfCondToken(type = QfCondTokenType.ATOM, atom = @QfCondition(attributeName = "b", isNotEmpty = true)),
@QfCondToken(type = QfCondTokenType.OR),
@QfCondToken(type = QfCondTokenType.ATOM, atom = @QfCondition(attributeName = "c", notEqual = "N")),
@QfCondToken(type = QfCondTokenType.RPAREN)
})| Attribute | Type | Description | Default |
|---|---|---|---|
value | @QfCondToken[] | Ordered token stream forming the expression | (required) |
@QfCondToken / QfCondTokenType
One token in a condition expression.
| Attribute | Type | Description | Default |
|---|---|---|---|
type | QfCondTokenType | Token type | (required) |
atom | @QfCondition | Atomic condition (used only when type is ATOM) | @QfCondition |
QfCondTokenType values: ATOM, AND, OR, LPAREN, RPAREN
@QfCondition
A single atomic comparison predicate.
| Attribute | Type | Description | Default |
|---|---|---|---|
source | Source | Where the comparison target value is resolved from | other_attribute_value |
attributeName | String | Target attribute name (used with other_attribute_value) | "" |
masterEntityAttributeName | String | Master entity attribute name (used with master_entity) | "" |
equal | String | Equality (=) comparison value | "" |
notEqual | String | Inequality (!=) comparison value | "" |
like | String | LIKE comparison pattern | "" |
notLike | String | NOT LIKE comparison pattern | "" |
in | String[] | IN comparison value list | {} |
notIn | String[] | NOT IN comparison value list | {} |
lessThan | String | Less-than (<) comparison value | "" |
lessThanOrEqual | String | Less-than-or-equal (<=) comparison value | "" |
moreThan | String | Greater-than (>) comparison value | "" |
moreThanOrEqual | String | Greater-than-or-equal (>=) comparison value | "" |
have | String | Privilege possession condition (used with privilege) | "" |
notHave | String | Privilege non-possession condition (used with privilege) | "" |
isEmpty | boolean | IS EMPTY condition | false |
isNotEmpty | boolean | IS NOT EMPTY condition | false |
treeDepth | int | Tree depth comparison value (used with tree_depth) | -1 |
Source values: other_attribute_value, master_entity, user_info, tree_depth, privilege, app, menu, capability
File / Media Annotations
@QfFile
Declares file upload metadata for an attribute.
@QfFile(maxFiles = 5, accept = "image/*")
private String thumbnailId;| Attribute | Type | Description | Default |
|---|---|---|---|
purpose | String | File purpose identifier | "file_purpose.general" |
maxFileSize | long | Maximum file size in bytes (0 = unlimited) | 0 |
maxFiles | int | Maximum number of files | 1 |
accept | String | Accepted MIME types (e.g. "image/*") | "*/*" |
defaultImage | String | Default image path when no file is uploaded | "thumb/defaultPicture.png" |
usePrimary | boolean | Whether to use the primary file only | false |
@QfZip
Declares a zip code (postal code) attribute. Automatically links to an address attribute for lookup integration.
@QfZip(addressAttributeName = "address", detailAddressAttributeName = "detailAddress")
private String zipCode;| Attribute | Type | Description | Default |
|---|---|---|---|
addressAttributeName | String | Attribute name that receives the resolved address | (required) |
detailAddressAttributeName | String | Attribute name that receives the detail address | "" |
Text Composition Annotations
@QfAffixes
Declares fixed prefix/suffix segments automatically prepended or appended on create/update.
@QfAffixes(
prefixes = { @QfTextSegment(source = QfTextSegment.Source.static_value, value = "PREFIX-") },
postfixes = { @QfTextSegment(source = QfTextSegment.Source.static_value, value = "-SUFFIX") }
)
private String code;| Attribute | Type | Description | Default |
|---|---|---|---|
prefixes | @QfTextSegment[] | Prefix segment definitions | {} |
postfixes | @QfTextSegment[] | Postfix segment definitions | {} |
@QfTextSegment (element)
One segment in a composed text expression. Used as a nested element in @QfAffixes, @QfComposedText, etc.
| Attribute | Type | Description | Default |
|---|---|---|---|
source | Source | Where the segment value is resolved from | this_attribute_value |
value | String | Static value or attribute name / lookup key depending on source | "" |
Source values
| Value | Description |
|---|---|
this_attribute_value | Uses the current attribute's value |
other_attribute_value | Uses another attribute's value (specify via value) |
user_info | Uses information from the current user context |
master_entity | Uses a value from the master entity |
static_value | Uses the literal string in value |
unknown | Unresolved / implementation-defined |
View-Specific Attribute Annotations
@QfExcelAttribute
Declares that an attribute should be included in Excel export output.
@QfExcelAttribute(order = 1)
private String productName;| Attribute | Type | Description | Default |
|---|---|---|---|
order | int | Column order in the Excel output | 0 |
exposeOn | @QfExposeOn[] | Per-app/capability exposure rules | {} |
@QfTreeAttribute
Declares that an attribute is exposed in tree view output.
@QfTreeAttribute(isName = true, sortable = true, order = 1)
private String categoryName;| Attribute | Type | Description | Default |
|---|---|---|---|
isName | boolean | Whether this attribute serves as the tree node display name | false |
order | int | Column order in the tree view | 0 |
sortable | boolean | Whether this column is sortable in tree view | false |
exposeOn | @QfExposeOn[] | Per-app/capability exposure rules | {} |
Persistence Annotations
@QfAllowedDirectAccess
Permits direct data access that bypasses Q-Framework managed abstractions. Required when qf.persistence.access.mode is permissive (default).
@QfAllowedDirectAccess(reason = "SPI implementation — must read user store directly")
private final UserRepository userRepository;| Attribute | Type | Description | Default |
|---|---|---|---|
reason | String | Reason for the bypass (serves as audit record) | "" |