;; Extension — global find/replace across text-bearing blocks. (st-bootstrap-classes!) (content/bootstrap!) (content-bootstrap-section!) (define d (doc-append (doc-append (doc-append (doc-empty "d") (mk-heading "h" 1 "Foo title")) (mk-text "p" "the Foo is here")) (mk-section "s" (list (mk-text "n" "nested Foo") (mk-image "img" "/foo.png" "Foo alt"))))) (define r (content/find-replace d "Foo" "Bar")) ;; ── replaces in heading + text ── (content-test "replace heading" (str (blk-send (doc-deep-find r "h") "text")) "Bar title") (content-test "replace text" (str (blk-send (doc-deep-find r "p") "text")) "the Bar is here") (content-test "replace nested text" (str (blk-send (doc-deep-find r "n") "text")) "nested Bar") ;; ── does NOT touch image alt/src (not a text field) ── (content-test "image alt untouched" (str (blk-send (doc-deep-find r "img") "alt")) "Foo alt") (content-test "image src untouched" (str (blk-send (doc-deep-find r "img") "src")) "/foo.png") ;; ── immutable ── (content-test "original unchanged" (str (blk-send (doc-deep-find d "p") "text")) "the Foo is here") ;; ── multiple occurrences in one block ── (content-test "all occurrences" (str (blk-send (doc-find (content/find-replace (doc-append (doc-empty "d") (mk-text "p" "a a a")) "a" "b") "p") "text")) "b b b") ;; ── code + quote text replaced ── (define d2 (doc-append (doc-append (doc-empty "d") (mk-code "c" "sx" "(old)")) (mk-quote "q" "src" "old saying"))) (define r2 (content/find-replace d2 "old" "new")) (content-test "replace code" (str (blk-send (doc-find r2 "c") "text")) "(new)") (content-test "replace quote" (str (blk-send (doc-find r2 "q") "text")) "new saying") ;; ── no match → unchanged render ── (content-test "no match" (asHTML (content/find-replace d "zzz" "qqq")) (asHTML d))