Molunerfinn/PicGo · warning

ALBUM_URL_REWRITE_TEMP_RULE_REQUIRED

Error message

ALBUM_URL_REWRITE_TEMP_RULE_REQUIRED

What it means

validateRuleOrThrow checks a URL rewrite rule before applying it to image URLs. It throws ALBUM_URL_REWRITE_TEMP_RULE_REQUIRED when either the `match` or `replace` part of an IUrlRewriteRule is empty/whitespace-only. The check runs before the regex is even compiled, so it guards against meaningless no-op or destructive empty patterns.

Source

Thrown at src/main/events/rpc/routes/albumToolbox/builtIn/changeURL.ts:41

  return value.map(item => {
    const raw = (item ?? {}) as Partial<Record<keyof IUrlRewriteRule, unknown>>
    return {
      match: String(raw.match ?? ''),
      replace: String(raw.replace ?? ''),
      enable: raw.enable === false ? false : true,
      global: raw.global === true,
      ignoreCase: raw.ignoreCase === true
    }
  }).filter(rule => rule.match.length > 0)
}

function buildFlags (rule: Pick<IUrlRewriteRule, 'global' | 'ignoreCase'>): string {
  return `${rule.global ? 'g' : ''}${rule.ignoreCase ? 'i' : ''}`
}

function validateRuleOrThrow (rule: IUrlRewriteRule) {
  if (!rule.match.trim() || !rule.replace.trim()) {
    throw new Error(T('ALBUM_URL_REWRITE_TEMP_RULE_REQUIRED'))
  }
  try {
    new RegExp(rule.match, buildFlags(rule))
  } catch (error) {
    const message = `Invalid URL rewrite regex pattern "${rule.match}": ${error instanceof Error ? error.message : String(error)}`
    logger.error(message)
    throw new Error(message)
  }
}

function applyFirstMatchRewrite (ctx: IPicGo, imgItem: ImgInfo, rules: IUrlRewriteRule[]): ImgInfo {
  const imgInfo = {
    imgUrl: imgItem.imgUrl,
    originImgUrl: imgItem.originImgUrl
  }
  PicGoUtils.applyUrlRewriteToImgInfo(imgInfo, rules, {
    log: {
      error: (...args: Parameters<IPicGo['log']['error']>) => ctx.log.error(...args),

View on GitHub (pinned to 07ec7068a5)

Solutions

  1. Fill in a non-empty `match` regex and a `replace` string before submitting the rule
  2. Trim the fields client-side and disable the submit button until both are non-empty
  3. If the intent is to remove a matched prefix, use an empty `replace` only with a non-empty `match` — the current validation requires both non-empty, so adjust the rule accordingly

Example fix

// before
const rule = { match: '', replace: '/new/', global: true, ignoreCase: false }
await changeURL(rule) // throws ALBUM_URL_REWRITE_TEMP_RULE_REQUIRED
// after
const rule = { match: 'old-host\\.com', replace: '/new/', global: true, ignoreCase: false }
if (rule.match.trim() && rule.replace.trim()) await changeURL(rule)
Defensive patterns

Strategy: validation

Validate before calling

function isRuleComplete(rule) {
  return typeof rule.match === 'string' && rule.match.trim() !== '' &&
         typeof rule.replace === 'string' && rule.replace.trim() !== ''
}
if (!isRuleComplete(rule)) throw new Error('match and replace are required')

Type guard

function isValidRewriteRule(rule) {
  return !!rule && typeof rule === 'object' &&
    typeof rule.match === 'string' && rule.match.trim() !== '' &&
    typeof rule.replace === 'string' && rule.replace.trim() !== ''
}

Try / catch

try {
  await changeURL(rule)
} catch (e) {
  if (e.message.includes('ALBUM_URL_REWRITE_TEMP_RULE_REQUIRED')) {
    showFormError('Match and replace fields are required')
  } else throw e
}

Prevention

When it happens

Trigger: Calling the changeURL RPC route (handle) with a rule whose `match` is '' or ' ', or whose `replace` is empty, e.g. submitting the rewrite form without filling both fields.

Common situations: User clicks apply in the album URL-rewrite UI with an untouched form; programmatic rule creation that defaults match/replace to empty strings; clearing the replace field intending a deletion but leaving match empty too.

Related errors


AI-assisted analysis of Molunerfinn/PicGo@07ec7068a5 (2026-08-30). Data as JSON: /api/errors/0b4bf0e2df37e09f. Report an issue: GitHub.