[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"navigation":3,"url-settings":86,"blog-\u002Fblog\u002Funderstanding-go-reflection-interfaces":671,"blog-author-\u002Fblog\u002Funderstanding-go-reflection-interfaces":1330,"i-material-symbols:arrow-back-rounded":1342},{"id":4,"extension":5,"footer":6,"header":73,"meta":83,"stem":84,"__hash__":85},"navigation\u002Fdata\u002Fshared\u002Fnavigation.yml","yml",{"brand":7,"columns":13,"legal":63},{"name":8,"tagline":9,"downloadCta":10},"Pieces","The memory layer for modern work.",{"label":11,"href":12},"All downloads","\u002Fdownloads",[14,26,39,51],{"title":15,"links":16},"Product",[17,20,23],{"label":18,"href":19},"Pieces Desktop","\u002F",{"label":21,"href":22},"Pieces Enterprise","\u002Fenterprise",{"label":24,"href":25},"Pieces MCP","\u002Fmcp",{"title":27,"links":28},"Resources",[29,33,36],{"label":30,"href":31,"external":32},"Documentation","url:docs.home",true,{"label":34,"href":35},"Blog","\u002Fblog",{"label":37,"href":38,"external":32},"GitHub","url:github.org",{"title":40,"links":41},"Community",[42,45,48],{"label":43,"href":44,"external":32},"Discord","url:social.discord",{"label":46,"href":47,"external":32},"X \u002F Twitter","url:social.x",{"label":49,"href":50,"external":32},"LinkedIn","url:social.linkedin",{"title":52,"links":53},"Company",[54,57,60],{"label":55,"href":56},"About","\u002Fabout",{"label":58,"href":59},"Updates","\u002Fupdates",{"label":61,"href":62},"Contact","\u002Fcontact",[64,67,70],{"label":65,"href":66},"Privacy Policy","\u002Flegal\u002Fprivacy",{"label":68,"href":69},"Refund Policy","\u002Flegal\u002Frefund",{"label":71,"href":72},"Terms of Service","\u002Flegal\u002Fterms",{"links":74,"signIn":75,"contact":78,"cta":80},[],{"label":76,"href":77},"Manage account","url:portal.home",{"label":79,"href":62},"Get in touch",{"label":81,"href":82},"Download","url:routes.downloads",{},"data\u002Fshared\u002Fnavigation","XlSALC7vYCXHcmcXnjJViwIZKsqnQWF4bn4o9RrcSBE",{"id":87,"extension":5,"links":88,"meta":668,"stem":669,"__hash__":670},"urlSettings\u002Fdata\u002Fshared\u002Furls.yml",[89,93,97,101,105,109,113,117,121,125,129,133,137,141,145,149,153,157,161,165,169,173,177,181,185,189,192,196,200,204,208,212,216,220,224,228,232,236,240,244,248,252,256,260,264,268,272,276,280,284,288,292,296,300,303,307,311,314,318,322,326,330,334,338,342,346,350,354,358,362,366,370,374,378,382,386,390,394,398,402,406,410,414,418,422,426,430,434,438,442,446,450,454,458,461,465,469,473,477,481,485,488,491,494,497,501,505,508,512,516,520,524,528,532,536,540,544,548,552,556,559,563,567,571,575,579,582,585,588,592,595,599,603,607,611,614,618,622,625,628,631,635,639,643,646,649,652,656,660,664],{"key":90,"label":91,"href":92},"downloads.desktop","Desktop download page","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop\u002Fdownload",{"key":94,"label":95,"href":96},"downloads.macOS.dmgArm64","macOS DMG Apple Silicon","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fpieces_for_x\u002Fdmg-arm64\u002Fdownload",{"key":98,"label":99,"href":100},"downloads.macOS.dmgIntel","macOS DMG Intel","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fpieces_for_x\u002Fdmg\u002Fdownload",{"key":102,"label":103,"href":104},"downloads.macOS.pkg","macOS PKG","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fmacos_packaging\u002Fpkg\u002Fdownload",{"key":106,"label":107,"href":108},"downloads.macOS.universal","Desktop macOS Universal","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fpieces_for_x\u002Fmacos-universal\u002Fdownload",{"key":110,"label":111,"href":112},"downloads.macOS.pkgArm64","Desktop macOS PKG Apple Silicon","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fmacos_packaging\u002Fpkg-pfd-arm64\u002Fdownload",{"key":114,"label":115,"href":116},"downloads.macOS.pkgIntel","Desktop macOS PKG Intel","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fmacos_packaging\u002Fpkg-pfd\u002Fdownload",{"key":118,"label":119,"href":120},"downloads.windows.appinstaller","Windows App Installer","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fappinstaller\u002Fpieces_for_x.appinstaller",{"key":122,"label":123,"href":124},"downloads.windows.exe","Windows EXE","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fpieces_for_x\u002Fwindows-exe\u002Fdownload",{"key":126,"label":127,"href":128},"downloads.windows.msix","Windows MSIX","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fpieces_for_x\u002Fwindows-msix\u002Fdownload",{"key":130,"label":131,"href":132},"downloads.windows.suiteManager","Windows Suite Manager","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fpieces_suite_windows\u002Fappinstaller\u002Fdownload",{"key":134,"label":135,"href":136},"downloads.linux.flatpakRepo","Linux Flatpak repository","https:\u002F\u002Fbuilds.pieces.app\u002Fpieces-flatpak-repo\u002Fpieces-flatpak.flatpakrepo",{"key":138,"label":139,"href":140},"downloads.linux.snapDesktop","Linux Snap Desktop","https:\u002F\u002Fsnapcraft.io\u002Fpieces-for-developers",{"key":142,"label":143,"href":144},"downloads.linux.snapPiecesOS","Linux Snap PiecesOS","https:\u002F\u002Fsnapcraft.io\u002Fpieces-os",{"key":146,"label":147,"href":148},"downloads.linux.snap","Desktop Linux Snap package","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fpieces_for_x\u002Fsnap\u002Fdownload",{"key":150,"label":151,"href":152},"downloads.piecesOS.macOS.dmgArm64","PiecesOS macOS DMG Apple Silicon","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fos_server\u002Fdmg-arm64\u002Fdownload",{"key":154,"label":155,"href":156},"downloads.piecesOS.macOS.dmgIntel","PiecesOS macOS DMG Intel","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fos_server\u002Fdmg\u002Fdownload",{"key":158,"label":159,"href":160},"downloads.piecesOS.macOS.universal","PiecesOS macOS Universal","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fos_server\u002Fmacos-universal\u002Fdownload",{"key":162,"label":163,"href":164},"downloads.piecesOS.macOS.pkgArm64","PiecesOS macOS PKG Apple Silicon","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fmacos_packaging\u002Fpkg-pos-launch-only-arm64\u002Fdownload",{"key":166,"label":167,"href":168},"downloads.piecesOS.macOS.pkgIntel","PiecesOS macOS PKG Intel","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fmacos_packaging\u002Fpkg-pos-launch-only\u002Fdownload",{"key":170,"label":171,"href":172},"downloads.piecesOS.windows.appinstaller","PiecesOS Windows App Installer","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fappinstaller\u002Fos_server.appinstaller",{"key":174,"label":175,"href":176},"downloads.piecesOS.windows.exe","PiecesOS Windows EXE","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fos_server\u002Fwindows-exe\u002Fdownload",{"key":178,"label":179,"href":180},"downloads.piecesOS.windows.msix","PiecesOS Windows MSIX","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fos_server\u002Fwindows-msix\u002Fdownload",{"key":182,"label":183,"href":184},"downloads.piecesOS.linux.snap","PiecesOS Linux Snap package","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fos_server\u002Fsnap\u002Fdownload",{"key":186,"label":187,"href":188},"downloads.combined.macOS.appleSilicon","Combined macOS installer Apple Silicon","https:\u002F\u002Fbuilds.pieces.app\u002Fstages\u002Fproduction\u002Fmacos_packaging\u002Fpkg-arm64\u002Fdownload",{"key":190,"label":191,"href":104},"downloads.combined.macOS.intel","Combined macOS installer Intel",{"key":193,"label":194,"href":195},"downloads.guides.macOS","macOS installation guide","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Fmacos-installation-guide",{"key":197,"label":198,"href":199},"downloads.guides.windows","Windows installation guide","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Fwindows-installation-guide",{"key":201,"label":202,"href":203},"downloads.guides.linux","Linux installation guide","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Flinux-installation-guide",{"key":205,"label":206,"href":207},"downloads.guides.linuxFlatpak","Linux Flatpak installation guide","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Flinux-installation-guide\u002Fflatpak",{"key":209,"label":210,"href":211},"downloads.guides.linuxSnap","Linux Snap installation guide","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Flinux-installation-guide\u002Fsnap",{"key":213,"label":214,"href":215},"downloads.guides.piecesOS","PiecesOS manual installation","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fcore-dependencies\u002Fpieces-os\u002Fmanual-installation",{"key":217,"label":218,"href":219},"extensions.chrome","Chrome extension","https:\u002F\u002Fchrome.google.com\u002Fwebstore\u002Fdetail\u002Fpieces-save-code-snippets\u002Figbgibhbfonhmjlechmeefimncpekepm",{"key":221,"label":222,"href":223},"extensions.firefox","Firefox add-on","https:\u002F\u002Faddons.mozilla.org\u002Fen-US\u002Ffirefox\u002Faddon\u002Fpieces-save-code-from-the-web\u002F",{"key":225,"label":226,"href":227},"extensions.edge","Edge add-on","https:\u002F\u002Fmicrosoftedge.microsoft.com\u002Faddons\u002Fdetail\u002Fpieces-save-code-snippet\u002Fhglfimcdgonaeeobjckfdabcldfidmim",{"key":229,"label":230,"href":231},"extensions.vscode","VS Code extension","https:\u002F\u002Fmarketplace.visualstudio.com\u002Fitems?itemName=MeshIntelligentTechnologiesInc.pieces-vscode",{"key":233,"label":234,"href":235},"extensions.visualStudio","Visual Studio extension","https:\u002F\u002Fmarketplace.visualstudio.com\u002Fitems?itemName=MeshIntelligentTechnologiesInc.PiecesVisualStudio",{"key":237,"label":238,"href":239},"extensions.jetbrains","JetBrains plugin","https:\u002F\u002Fplugins.jetbrains.com\u002Fplugin\u002F17328-pieces--save-search-share--reuse-code-snippets",{"key":241,"label":242,"href":243},"extensions.obsidian","Obsidian plugin","https:\u002F\u002Fobsidian.md\u002Fplugins?id=pieces-for-developers",{"key":245,"label":246,"href":247},"extensions.sublime","Sublime package","https:\u002F\u002Fpackagecontrol.io\u002Fpackages\u002FPieces",{"key":249,"label":250,"href":251},"extensions.neovim","Neovim plugin","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fplugin_neo_vim",{"key":253,"label":254,"href":255},"extensions.jupyterlab","JupyterLab plugin","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fjupyterlab-pieces",{"key":257,"label":258,"href":259},"extensions.cli","Pieces CLI","https:\u002F\u002Fpypi.org\u002Fproject\u002Fpieces-cli\u002F",{"key":261,"label":262,"href":263},"docs.home","Documentation home","https:\u002F\u002Fdocs.pieces.app",{"key":265,"label":266,"href":267},"docs.getStarted","Get started docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces",{"key":269,"label":270,"href":271},"docs.api","API docs","https:\u002F\u002Fdocs.pieces.app\u002Fapi",{"key":273,"label":274,"href":275},"docs.desktop.overview","Desktop overview","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop",{"key":277,"label":278,"href":279},"docs.desktop.onboarding","Desktop onboarding","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop\u002Fonboarding",{"key":281,"label":282,"href":283},"docs.desktop.timeline","Desktop timeline docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop\u002Ftimeline",{"key":285,"label":286,"href":287},"docs.desktop.summaries","Desktop summaries docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop\u002Fsingle-click-summaries",{"key":289,"label":290,"href":291},"docs.desktop.search","Desktop conversational search docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop\u002Fconversational-search",{"key":293,"label":294,"href":295},"docs.desktop.drive","Desktop drive docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop\u002Fdrive",{"key":297,"label":298,"href":299},"docs.desktop.account","Desktop account settings docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fdesktop\u002Fconfiguration\u002Faccount",{"key":301,"label":302,"href":92},"docs.desktop.download","Desktop download docs",{"key":304,"label":305,"href":306},"docs.piecesOS.overview","PiecesOS overview docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fcore-dependencies",{"key":308,"label":309,"href":310},"docs.piecesOS.details","PiecesOS details docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fcore-dependencies\u002Fpieces-os",{"key":312,"label":313,"href":215},"docs.piecesOS.install","PiecesOS install docs",{"key":315,"label":316,"href":317},"docs.piecesOS.quickMenu","PiecesOS quick menu docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fcore-dependencies\u002Fpieces-os\u002Fquick-menu",{"key":319,"label":320,"href":321},"docs.piecesOS.storage","On-device storage docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fcore-dependencies\u002Fon-device-storage",{"key":323,"label":324,"href":325},"docs.piecesOS.troubleshooting","PiecesOS troubleshooting docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fcore-dependencies\u002Fpieces-os\u002Ftroubleshooting",{"key":327,"label":328,"href":329},"docs.mcp.overview","MCP overview docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp",{"key":331,"label":332,"href":333},"docs.mcp.cursor","MCP Cursor docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fcursor",{"key":335,"label":336,"href":337},"docs.mcp.vscode","MCP VS Code docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fvs-code",{"key":339,"label":340,"href":341},"docs.mcp.claudeDesktop","MCP Claude Desktop docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fclaude-desktop",{"key":343,"label":344,"href":345},"docs.mcp.claudeCode","MCP Claude Code docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fclaude-code",{"key":347,"label":348,"href":349},"docs.mcp.claudeCowork","MCP Claude Cowork docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fclaude-cowork",{"key":351,"label":352,"href":353},"docs.mcp.githubCopilot","MCP GitHub Copilot docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fgithub-copilot",{"key":355,"label":356,"href":357},"docs.mcp.goose","MCP Goose docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fgoose",{"key":359,"label":360,"href":361},"docs.mcp.windsurf","MCP Windsurf docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fwindsurf",{"key":363,"label":364,"href":365},"docs.mcp.zed","MCP Zed docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fzed",{"key":367,"label":368,"href":369},"docs.mcp.jetbrains","MCP JetBrains docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fjetbrains-ides",{"key":371,"label":372,"href":373},"docs.mcp.continueDev","MCP Continue docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fcontinue-dev",{"key":375,"label":376,"href":377},"docs.mcp.cline","MCP Cline docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fcline",{"key":379,"label":380,"href":381},"docs.mcp.raycast","MCP Raycast docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fraycast",{"key":383,"label":384,"href":385},"docs.mcp.rovoDevCli","MCP Rovo Dev CLI docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Frovo-dev-cli",{"key":387,"label":388,"href":389},"docs.mcp.openaiCodexCli","MCP OpenAI Codex CLI docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fopenai-codex-cli",{"key":391,"label":392,"href":393},"docs.mcp.googleGeminiCli","MCP Google Gemini CLI docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fgoogle-gemini-cli",{"key":395,"label":396,"href":397},"docs.mcp.amazonQ","MCP Amazon Q docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Famazon-q-developer",{"key":399,"label":400,"href":401},"docs.mcp.chatgptDev","MCP ChatGPT Developer Mode docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fchatgpt-developer-mode",{"key":403,"label":404,"href":405},"docs.mcp.openclaw","MCP OpenClaw docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fopenclaw",{"key":407,"label":408,"href":409},"docs.mcp.mcpRemote","MCP Remote docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fmcp-remote",{"key":411,"label":412,"href":413},"docs.mcp.ngrok","MCP ngrok docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmcp\u002Fngrok-setup",{"key":415,"label":416,"href":417},"docs.troubleshooting.macOS","macOS troubleshooting docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Ftroubleshooting\u002Fmacos",{"key":419,"label":420,"href":421},"docs.troubleshooting.windows","Windows troubleshooting docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Ftroubleshooting\u002Fwindows",{"key":423,"label":424,"href":425},"docs.troubleshooting.linux","Linux troubleshooting docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fmeet-pieces\u002Ftroubleshooting\u002Flinux",{"key":427,"label":428,"href":429},"docs.privacy","Privacy and security docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fprivacy-security-your-data",{"key":431,"label":432,"href":433},"docs.support","Support docs","https:\u002F\u002Fdocs.pieces.app\u002Fproducts\u002Fsupport",{"key":435,"label":436,"href":437},"portal.home","Pieces portal","https:\u002F\u002Fportal.pieces.app",{"key":439,"label":440,"href":441},"site.home","Website home","https:\u002F\u002Fpieces.app",{"key":443,"label":444,"href":445},"site.about","About page","https:\u002F\u002Fpieces.app\u002Fabout",{"key":447,"label":448,"href":449},"site.features","Features page","https:\u002F\u002Fpieces.app\u002Ffeatures",{"key":451,"label":452,"href":453},"site.plugins","Plugins page","https:\u002F\u002Fpieces.app\u002Fplugins",{"key":455,"label":456,"href":457},"site.contact","Contact page","https:\u002F\u002Fpieces.app\u002Fcontact",{"key":459,"label":58,"href":460},"site.updates","https:\u002F\u002Fpieces.app\u002Fupdates",{"key":462,"label":463,"href":464},"site.news","News","https:\u002F\u002Fpieces.app\u002Fnews",{"key":466,"label":467,"href":468},"site.events","Community events","https:\u002F\u002Fpieces.app\u002Fcommunity\u002Fevents",{"key":470,"label":471,"href":472},"site.userStories","User stories","https:\u002F\u002Fpieces.app\u002Fuser-stories",{"key":474,"label":475,"href":476},"site.academy","Academy","https:\u002F\u002Fpieces.app\u002Flearn\u002Facademy",{"key":478,"label":479,"href":480},"site.support","Website support","https:\u002F\u002Fpieces.app\u002Fsupport",{"key":482,"label":483,"href":484},"site.standup","Standup","https:\u002F\u002Fpieces.app\u002Fstandup",{"key":486,"label":34,"href":487},"site.blog","https:\u002F\u002Fcode.pieces.app\u002Fblog",{"key":489,"label":43,"href":490},"social.discord","https:\u002F\u002Fdiscord.gg\u002Fgetpieces",{"key":492,"label":46,"href":493},"social.x","https:\u002F\u002Fx.com\u002Fgetpieces",{"key":495,"label":496,"href":493},"social.twitter","Twitter",{"key":498,"label":499,"href":500},"social.instagram","Instagram","https:\u002F\u002Fwww.instagram.com\u002Fgetpieces\u002F",{"key":502,"label":503,"href":504},"social.tiktok","TikTok","https:\u002F\u002Fwww.tiktok.com\u002F@getpieces",{"key":506,"label":49,"href":507},"social.linkedin","https:\u002F\u002Fwww.linkedin.com\u002Fcompany\u002Fgetpieces\u002F",{"key":509,"label":510,"href":511},"social.youtube","YouTube","https:\u002F\u002Fyoutube.com\u002F@getpieces",{"key":513,"label":514,"href":515},"github.org","GitHub organization","https:\u002F\u002Fgithub.com\u002Fpieces-app",{"key":517,"label":518,"href":519},"github.support","GitHub support","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fsupport",{"key":521,"label":522,"href":523},"github.issues","GitHub issues","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fsupport\u002Fissues",{"key":525,"label":526,"href":527},"github.discussions","GitHub discussions","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fsupport\u002Fdiscussions",{"key":529,"label":530,"href":531},"github.documentation","GitHub documentation","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fdocumentation",{"key":533,"label":534,"href":535},"github.opensource","GitHub open source","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fopensource",{"key":537,"label":538,"href":539},"github.sdks.python","Python SDK","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fpieces-os-client-sdk-for-python",{"key":541,"label":542,"href":543},"github.sdks.typescript","TypeScript SDK","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fpieces-os-client-sdk-for-typescript",{"key":545,"label":546,"href":547},"github.sdks.dart","Dart SDK","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fpieces-os-client-sdk-for-dart",{"key":549,"label":550,"href":551},"github.sdks.kotlin","Kotlin SDK","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fpieces-os-client-sdk-for-kotlin",{"key":553,"label":554,"href":555},"github.plugins.obsidian","Obsidian plugin repository","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fobsidian-pieces",{"key":557,"label":558,"href":255},"github.plugins.jupyterlab","JupyterLab plugin repository",{"key":560,"label":561,"href":562},"github.plugins.sublime","Sublime plugin repository","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fplugin_sublime",{"key":564,"label":565,"href":566},"github.plugins.neovim","Neovim plugin repository","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fplugin_neovim",{"key":568,"label":569,"href":570},"github.cliAgent","CLI agent repository","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fcli-agent",{"key":572,"label":573,"href":574},"github.mcpDart","MCP Dart repository","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fmcp_dart",{"key":576,"label":577,"href":578},"github.awesomePieces","Awesome Pieces repository","https:\u002F\u002Fgithub.com\u002Fpieces-app\u002Fawesome-pieces",{"key":580,"label":581,"href":66},"legal.privacyPolicy","Privacy policy",{"key":583,"label":584,"href":69},"legal.refundPolicy","Refund policy",{"key":586,"label":587,"href":72},"legal.terms","Terms",{"key":589,"label":590,"href":591},"legal.security","Legal security","https:\u002F\u002Fpieces.app\u002Flegal\u002Fsecurity",{"key":593,"label":594,"href":511},"videos.youtubeChannel","YouTube channel",{"key":596,"label":597,"href":598},"videos.gettingStartedDesktop","Getting started desktop video","https:\u002F\u002Fyoutu.be\u002FdUr1lRM_TYk",{"key":600,"label":601,"href":602},"videos.snippetDiscoveryxR","Snippet discovery video","https:\u002F\u002Fyoutu.be\u002FG6vb1USw-30",{"key":604,"label":605,"href":606},"sales.bookACall","Book a sales call","https:\u002F\u002Fcalendar.app.google\u002FWVUDtUfNy5Vst3sH7",{"key":608,"label":609,"href":610},"sales.enterprise","Enterprise form","https:\u002F\u002Fgetpieces.typeform.com\u002Fto\u002FaVQFTvpE",{"key":612,"label":613,"href":527},"sales.feedback","Feedback discussions",{"key":615,"label":616,"href":617},"sales.earlyAccess","Early access form","https:\u002F\u002Fgetpieces.typeform.com\u002Fearlyaccess",{"key":619,"label":620,"href":621},"sales.supportEmail","Support email","mailto:support@pieces.app",{"key":623,"label":624,"href":19},"routes.home","Home route",{"key":626,"label":627,"href":56},"routes.about","About route",{"key":629,"label":630,"href":12},"routes.downloads","Downloads route",{"key":632,"label":633,"href":634},"routes.thanks","Post-install thanks route","\u002Finstall\u002Fthanks",{"key":636,"label":637,"href":638},"routes.pricing","Pricing route","\u002Fpricing",{"key":640,"label":641,"href":642},"cta.freeTrial","Start free trial CTA (Pieces Pro) — used by \u002Fcampaigns\u002F* landing pages","https:\u002F\u002Fcampaigns.pieces.app\u002F",{"key":644,"label":645,"href":22},"routes.enterprise","Enterprise route",{"key":647,"label":648,"href":62},"routes.contact","Contact route",{"key":650,"label":651,"href":59},"routes.updates","Updates route",{"key":653,"label":654,"href":655},"routes.migrationError","Migration error route","\u002Fmigration\u002Ferror",{"key":657,"label":658,"href":659},"routes.authenticated","Post-login authenticated route","\u002Fauth\u002Fsigned-in",{"key":661,"label":662,"href":663},"routes.signed-out","Signed out route","\u002Fauth\u002Fsigned-out",{"key":665,"label":666,"href":667},"routes.authentication-error","Authentication error route","\u002Fauth\u002Ferror",{},"data\u002Fshared\u002Furls","2AvfSWI6bZACH5Kr1ZS3txMLjteRjCjbDR_ul1uRZ9Q",{"id":672,"title":673,"author":674,"authorPhoto":675,"authorPhotoAlt":676,"authorSlug":677,"body":678,"buttonText":676,"buttonUrl":676,"category":1316,"date":1317,"description":1318,"draft":1319,"editorsPick":1319,"extension":1320,"featured":1319,"image":1321,"imageAlt":1322,"meta":1323,"navigation":32,"ogImage":676,"ogImageAlt":676,"path":1324,"seo":1325,"stem":1326,"tags":1327,"__hash__":1329},"blog\u002Fblog\u002Funderstanding-go-reflection-interfaces.md","Understanding Reflection and Interfaces in the Go Programming Language","Ikeh Chukwuka Favour","https:\u002F\u002Fstorage.googleapis.com\u002Fpieces-marketing-website\u002Fimages\u002Fauthors\u002Fisaac-junior.svg",null,"ikeh-chukwuka-favour",{"type":679,"value":680,"toc":1306},"minimark",[681,698,703,706,709,736,747,756,761,767,796,809,815,821,827,833,861,865,870,873,876,882,892,901,907,913,917,923,931,935,942,948,954,972,978,984,994,1000,1006,1010,1016,1019,1030,1036,1042,1045,1059,1079,1085,1091,1097,1128,1137,1143,1149,1171,1186,1192,1197,1202,1206,1215,1221,1227,1231,1237,1284,1288],[682,683,684,685,689,690,693,694,697],"p",{},"This article will look at the ",[686,687,688],"strong",{},"Reflection and Interface"," concepts that Go provides as part of its collection of features. ",[686,691,692],{},"Reflection"," gives us the flexibility to dynamically inspect and learn about the type of an arbitrary object along with information about its intrinsic structure. ",[686,695,696],{},"Interface"," on its own dynamics helps identify, abstract, and define behavioral patterns that different data types can share.",[699,700,702],"h2",{"id":701},"what-is-reflection-in-go","What is Reflection in Go?",[682,704,705],{},"Go uses static typing, meaning every variable has precisely one fixed type known at build time, known as its static type. With that well stated, there’s then a concern of how to deal and interact with data types that do not yet exist when you implement your code, but may exist in the future.",[682,707,708],{},"In its simplest form, reflection is the capacity of a program to examine\u002Finspect its own values and variables during execution and determine their type. A familiar scenario where reflection allows us to inspect and manipulate unknown structures is decoding JSON data. Another scenario would be when working with data types that don't implement a common interface and thus have peculiar or unknown behaviors.",[682,710,711,712,715,716,719,720,723,724,727,728,731,732,735],{},"Reflection is built around three concepts: ",[686,713,714],{},"Types",", ",[686,717,718],{},"Kinds",", and ",[686,721,722],{},"Values",". The ",[686,725,726],{},"Kind"," can be struct, int, string, slice, map, or any other Go primitive type. If you define a struct named Foo, the Kind is a ",[686,729,730],{},"struct,"," and the Type is ",[686,733,734],{},"Foo",". The types and functions used to implement reflection in Go reside in the standard library's reflect package. Let’s look at some helpful functions defined within the reflect package:",[737,738,743],"pre",{"className":739,"code":741,"language":742},[740],"language-text","\u002F\u002F go\npackage main\nimport (\n \"fmt\"\n \"reflect\"\n)\ntype Foo struct {\n  addr string\n  dip  Dip\n}\ntype Dip struct {\n  name string\n  age  int\n}\nvar data = Foo{\n  dip: Dip{name: \"Alice\", age: 10},\n  addr: \"alton street\",\n}\nfunc main() {\n \u002F\u002F Inspect the reflection Type of a variable\n  rt := reflect.TypeOf(data)\n  fmt.Println(rt)\n \u002F\u002F Inspect the reflection Value of a variable\n  rv := reflect.ValueOf(data)\n  fmt.Println(rv)\n \u002F\u002F Alternatively\n  rt = rv.Type()\n  fmt.Println(rt)\n \u002F\u002F Inspect the reflection Kind of a variable\n  rk := rv.Kind()\n  fmt.Println(rk)\n \u002F\u002F Inspect the reflection Name of a variable\n  rn := rt.Name()\n  fmt.Println(rn)\n \u002F\u002F Traverse the fields of a struct.\n if rt.Kind() == reflect.Struct {\n for i := 0; i \u003C rt.NumField(); i++ {\n      fv := rv.Field(i)\n      fmt.Println(fv)\n    }\n  }\n \u002F\u002F Inspect the underlying contained type in a variable\n  rt = reflect.TypeOf([2]int {1, 2})\n  ct = ct.Elem()\n  fmt.Println(ct)\n}\n","text",[744,745,741],"code",{"__ignoreMap":746},"",[682,748,749],{},[750,751,755],"a",{"href":752,"rel":753},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=e6a84ab2a6",[754],"nofollow","Save this code",[682,757,758],{},[686,759,760],{},"Output:",[737,762,765],{"className":763,"code":764,"language":742},[740],"\u002F\u002F terminal\nmain.Foo\n{alton street {Alice 10}}\nmain.Foo\nstruct\nFoo\nalton street\n{Alice 10}\nint\n",[744,766,764],{"__ignoreMap":746},[682,768,769,770,772,773,776,777,780,781,784,785,788,789,784,792,795],{},"In the above snippet, we defined two structs, ",[744,771,734],{}," and ",[744,774,775],{},"Dip"," as our sample structures to use along with the ",[744,778,779],{},"reflection"," package. The ",[744,782,783],{},"reflect.TypeOf"," function returns ",[744,786,787],{},"reflect.Type",", which has methods defined on its type to provide other information about the type of the variable passed in. The ",[744,790,791],{},"reflect.ValueOf",[744,793,794],{},"reflect.Value",", which allows the reflection to read or write values.",[682,797,798,799,801,802,804,805,808],{},"In addition to reading, we can also use the ",[744,800,779],{}," package to modify\u002Fwrite the value of a structure. To modify a value using the ",[744,803,791],{}," function, we need to pass a pointer to the variable instead and call the ",[744,806,807],{},"Elem"," function, which will return the value at the pointer address.",[737,810,813],{"className":811,"code":812,"language":742},[740],"\u002F\u002F go\npackage main\nimport (\n \"fmt\"\n \"reflect\"\n)\ntype Pieces struct {\n  Id int\n  Content string\n  Rating float64\n}\nfunc main() {\n  data := Pieces{1, \"I come in peace, comrade!\", 4.1}\n  fmt.Printf(\"Original data: %+v\\n\", data)\n  mutData := reflect.ValueOf(&data).Elem()\n for i := 0; i \u003C mutData.NumField(); i++ {\n if mutData.Field(i).Kind() == reflect.Int {\n      mutData.Field(i).SetInt(12)\n    } else if mutData.Field(i).Kind() == reflect.String {\n      mutData.Field(i).SetString(\"No, I live for violence, comrade!\")\n    } else if mutData.Field(i).Kind() == reflect.Float64 {\n      mutData.Field(i).SetFloat(5.5)\n    }\n  }\n  fmt.Printf(\"Mutated data: %+v\\n\", data)\n}\n",[744,814,812],{"__ignoreMap":746},[682,816,817],{},[750,818,755],{"href":819,"rel":820},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=6e54499f8e",[754],[682,822,823,826],{},[686,824,825],{},"Output",":",[737,828,831],{"className":829,"code":830,"language":742},[740],"\u002F\u002F terminal\nOriginal data: {Id:1 Content:I come in peace, comrade! Rating:4.1}\nMutated data: {Id:12 Content:No, I live for violence, comrade! Rating:5.5}\n",[744,832,830],{"__ignoreMap":746},[682,834,835,836,715,839,842,843,846,847,850,851,856,857,860],{},"In the above snippet, notice the use of the ",[744,837,838],{},"SetInt",[744,840,841],{},"SetString",", and the ",[744,844,845],{},"SetFloat"," functions to write the new values of the structure. The ",[744,848,849],{},"reflect"," package defined more of these functions for changing the value of primitive data types. Find more info about the ",[750,852,855],{"href":853,"rel":854},"https:\u002F\u002Fpkg.go.dev\u002Freflect",[754],"reflect package",". Note, it’s a safe practice always to check if the value of the structure can be changed using the ",[744,858,859],{},"reflect.Value.CanSet"," function.",[699,862,864],{"id":863},"introduction-to-type-methods-and-interface-in-go","Introduction to Type methods and Interface in Go",[866,867,869],"h3",{"id":868},"type-methods","Type methods",[682,871,872],{},"When a function is attached to a specific data type, receiver argument, we consider this a type method in Go. The receiver argument gives the method the needed access to the underlying data type to either read it, write to it, or both.",[682,874,875],{},"We can define the type method using the following Go syntaxes:",[737,877,880],{"className":878,"code":879,"language":742},[740],"\u002F\u002F A copy of the receiver argument\nfunc (p Pieces) refChange() { } \u002F\u002F \u003C-- 1\n\u002F\u002F a pointer to the receiver argument\nfunc (p *Pieces) refChange() { } \u002F\u002F \u003C-- 2\n",[744,881,879],{"__ignoreMap":746},[682,883,884,885,888,889,891],{},"Defining a type method with the first syntax means we’re passing a copy of the value of the receiver argument to the ",[744,886,887],{},"refChange"," function. In the second definition, we defined and passed the pointer to the receiver argument instead of passing a copy of the receiver argument. This definition gives us direct access to the receiver argument in the ",[744,890,887],{}," function, meaning we can persist the changes made to the receiver argument.",[682,893,894,895,897,898,900],{},"Let’s implement a method on the ",[744,896,8],{}," struct to change the values of the struct using the ",[744,899,849],{}," package:",[737,902,905],{"className":903,"code":904,"language":742},[740],"\u002F\u002F go\n...\nfunc (p *Pieces) refChange(id int64, content string, rating float64) {\n  mutData := reflect.ValueOf(p).Elem()\n for i := 0; i \u003C mutData.NumField(); i++ {\n if mutData.Field(i).Kind() == reflect.Int {\n      mutData.Field(i).SetInt(id)\n    } else if mutData.Field(i).Kind() == reflect.String {\n      mutData.Field(i).SetString(content)\n    } else if mutData.Field(i).Kind() == reflect.Float64 {\n      mutData.Field(i).SetFloat(rating)\n      mutData.Field(i).CanSet()\n    }\n  }\n}\nfunc main() {\n  data := &Pieces{1, \"I come in peace, comrade!\", 4.1}\n  fmt.Printf(\"Original data: %+v\\n\", data)\n  data.refChange(100, \"No, peace is not an option comrade!\", 4.7)\n  fmt.Printf(\"Mutated data: %+v\\n\", data)\n}\n",[744,906,904],{"__ignoreMap":746},[682,908,909],{},[750,910,755],{"href":911,"rel":912},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=38ef428609",[754],[682,914,915,826],{},[686,916,825],{},[737,918,921],{"className":919,"code":920,"language":742},[740],"\u002F\u002F terminal\nOriginal data: {Id:1 Content:I come in peace, comrade! Rating:4.1}\nMutated data: {Id:100 Content:No, peace is not an option comrade! Rating:4.7}\n",[744,922,920],{"__ignoreMap":746},[682,924,925,926],{},"This is a simple introduction to the type method on structures in Go. ",[750,927,930],{"href":928,"rel":929},"https:\u002F\u002Fgo.dev\u002Fdoc\u002Feffective_go#methods",[754],"Learn more about the type method in the Go documentation.",[866,932,934],{"id":933},"interfaces","Interfaces",[682,936,937,938,941],{},"In Go, an ",[686,939,940],{},"interface"," is a mechanism for defining behavior that is implemented using a set of method signatures. The interface type describes the behavioral expectation of other types by defining a set of type methodsthat need to be implemented by these other types before claiming to support the behavior. In essence, interface works with type methods associated with a given data type; although we can use any data type in Go, it’s usually struct. So, before a Go type satisfies an interface type, it would need to implement all of the type methods defined by the interface type.",[737,943,946],{"className":944,"code":945,"language":742},[740],"...\ntype Blog interface {\n  ReadContent(string) (string, int)\n  GetRating() (float64)\n}\n...\n",[744,947,945],{"__ignoreMap":746},[682,949,950],{},[750,951,755],{"href":952,"rel":953},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=788340858c",[754],[682,955,956,957,772,960,963,964,772,966,968,969,971],{},"The above snippet defines an interface type with two function signatures, ",[744,958,959],{},"ReadContent",[744,961,962],{},"GetRating",". For a type in Go to implement this interface means it has ",[744,965,959],{},[744,967,962],{}," type methods defined. Let’s define these type methods for the ",[744,970,8],{}," struct:",[737,973,976],{"className":974,"code":975,"language":742},[740],"...\nfunc (p *Pieces) ReadContent(input string) (string, int) {\n if input != \"\" {\n    p.Content = input\n  }\n return p.Content, utf8.RuneCountInString(p.Content)\n}\nfunc (p *Pieces) GetRating() (float64) {\n return p.Rating\n}\n...\n",[744,977,975],{"__ignoreMap":746},[682,979,980],{},[750,981,755],{"href":982,"rel":983},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=409e458def",[754],[682,985,986,987,989,990,993],{},"In the above snippet, once we implemented the functions of an interface for the ",[744,988,8],{}," data type, that interface is satisfied automaticallyfor that data type. To make some sense out of these, let’s say we want to publish any post on our blog, but we want the post to be readable and rate-able. With the help of interface type, we can place some sort of boundary on a ",[744,991,992],{},"Publish"," function:",[737,995,998],{"className":996,"code":997,"language":742},[740],"...\nfunc Publish(post Blog) {\n if r := post.GetRating(); r != 0 {\n    c, rc := post.ReadContent(\"\")\n    fmt.Printf(\"New post: %s\\nWord count:%d\\tWith rating: %.1f\\n\", c, rc, r)\n  }\n}\n...\n",[744,999,997],{"__ignoreMap":746},[682,1001,1002],{},[750,1003,755],{"href":1004,"rel":1005},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=36de438801",[754],[682,1007,1008],{},[686,1009,760],{},[737,1011,1014],{"className":1012,"code":1013,"language":742},[740],"\u002F\u002F terminal\nNew post: No, peace is not an option comrade!\nWord count:35   With rating: 4.7\n",[744,1015,1013],{"__ignoreMap":746},[682,1017,1018],{},"Interfaces are abstract types that outline a set of methods that must be implemented for another type before it can be regarded as an instance of the interface. In other words, an interface consists of both a type and a collection of methods.",[682,1020,1021,1022,1025,1026,1029],{},"An ",[686,1023,1024],{},"empty interface"," is defined as just ",[744,1027,1028],{},"interface{}",". Since an empty interface has no methods, it can and is already implemented by every data type. For example, a slice which defines its elements as a type of empty interface means it can store anything in itself.",[737,1031,1034],{"className":1032,"code":1033,"language":742},[740],"\u002F\u002F gos := []interface{}{4, \"string\", 2.5, new(Pieces), true} \u002F\u002F [4 string 2.5 0x140000ae000 true]\n",[744,1035,1033],{"__ignoreMap":746},[682,1037,1038],{},[750,1039,755],{"href":1040,"rel":1041},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=b93243aa67",[754],[682,1043,1044],{},"It’s advised to sparingly make use of the empty interface, especially when storing sequences of data so as to avoid errors that are easily tracked down during compiling time.",[682,1046,1047,1048,1051,1052,719,1055,1058],{},"Let’s briefly look at three commonly used interfaces from the standard library shipped with Go upon installation. The three interfaces are the ",[744,1049,1050],{},"sort.Interface",", the ",[744,1053,1054],{},"io.Writer",[744,1056,1057],{},"io.Reader"," interfaces. Let’s briefly explain each below:",[1060,1061,1062],"ol",{},[1063,1064,1065,1066,1068,1069,1071,1072,1075,1076,1078],"li",{},"The ",[744,1067,1050],{},": The ",[744,1070,1050],{}," defines three necessary methods for custom implementation to sort a slice of custom data. The ",[744,1073,1074],{},"sort"," package contains the ",[744,1077,1050],{}," interface with the below definition:",[737,1080,1083],{"className":1081,"code":1082,"language":742},[740],"\u002F\u002F go\ntype Interface interface {\n  Len() int\n  Less(i, j int) bool\n  Swap(i, j int)\n}\n",[744,1084,1082],{"__ignoreMap":746},[682,1086,1087],{},[750,1088,755],{"href":1089,"rel":1090},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=37e3449b16",[754],[682,1092,1093,1094,1096],{},"Once we implement ",[744,1095,1050],{}," for our custom data stored in slices, the above three methods allow us to sort the slices according to our custom needs and data.",[1098,1099,1100,1106,1119],"ul",{},[1063,1101,1065,1102,1105],{},[744,1103,1104],{},"Len"," function returns the actual length of the slice being sorted.",[1063,1107,1065,1108,1111,1112,772,1115,1118],{},[744,1109,1110],{},"Less"," function contains the implementation of how the elements would be compared and sorted; this implementation would be custom to the needs of the developer but must return the boolean value of the comparison between the element at index ",[744,1113,1114],{},"i",[744,1116,1117],{},"j",".",[1063,1120,1065,1121,1124,1125,1127],{},[744,1122,1123],{},"Swap"," does the actual swapping of elements within the slice based on the outcome of ",[744,1126,1110],{},". This is required for the sorting algorithm to work.",[682,1129,1130,1131,1133,1134,1136],{},"2 . The ",[744,1132,1054],{},": This interface represents the writing part of the basis of file I\u002FO in Go. The operation of writing to either a file, network or any writable process, involves the implementation of ",[744,1135,1054],{}," for that writable object (data type). The interface definition is:",[737,1138,1141],{"className":1139,"code":1140,"language":742},[740],"\u002F\u002F go\ntype Writer interface {\n  Write(p []byte) (n int, err error)\n}\n",[744,1142,1140],{"__ignoreMap":746},[682,1144,1145],{},[750,1146,755],{"href":1147,"rel":1148},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=765343948b",[754],[682,1150,1151,1152,1155,1156,1159,1160,772,1163,1166,1167,1170],{},"The above interface definition needs only one function signature to satisfy the ",[744,1153,1154],{},"Writer"," interface. The ",[744,1157,1158],{},"Write"," function takes as its argument a byte slice containing the data we want to write to, either a file, network or any writable object, and returns two named values, ",[744,1161,1162],{},"n",[744,1164,1165],{},"err",". These values represent the number of bytes written and an ",[744,1168,1169],{},"error"," variable.",[1060,1172,1174],{"start":1173},3,[1063,1175,1065,1176,1178,1179,1182,1183,1185],{},[744,1177,1057],{},": This interface represents the reading part of the basis of file I\u002FO in Go–the operation of reading from either a file, network or any readable process. The ",[744,1180,1181],{},"Reader"," interface defines only one function signature just like ",[744,1184,1054],{},". Let’s look at the interface definition:",[737,1187,1190],{"className":1188,"code":1189,"language":742},[740],"\u002F\u002F go\ntype Reader interface {\n  Read(p []byte) (n int, err error)\n}\n",[744,1191,1189],{"__ignoreMap":746},[682,1193,1194],{},[750,1195,755],{"href":1147,"rel":1196},[754],[682,1198,1199,1200,1170],{},"The above definition takes as its argument a byte slice which we will fill with data being read from a file, a network, or any readable object. We fill the byte slice with data up to its length. The return values represent the number of bytes read and an ",[744,1201,1169],{},[699,1203,1205],{"id":1204},"use-cases-of-go-interface","Use cases of Go interface",[682,1207,1208,1209,1211,1212,1214],{},"The concept of interfaces is predominantly used across different Go packages and executable programs to achieve flexibility without affecting the program's performance. The following example will explore the use of ",[744,1210,1050],{}," to sort the ",[744,1213,8],{}," struct type:",[737,1216,1219],{"className":1217,"code":1218,"language":742},[740],"\u002F\u002F go\n...\ntype PSlice []Pieces\nfunc (ps PSlice) Len() int {\n return len(ps)\n}\nfunc (ps PSlice) Less(i, j int) bool {\n return ps[i].Id \u003C ps[j].Id\n}\nfunc (ps PSlice) Swap(i, j int) {\n  ps[i], ps[j] = ps[j], ps[i]\n}\n...\nfunc main() {\n  posts := []Pieces {\n    {7, \"I come in peace, comrade!\", 4.1},\n    {100, \"No, peace is not an option comrade!\", 4.7 },\n    {13, \"I preach violence, comrade!\", 4.5},\n    {-1, \"I live for violence, comrade\", 5.5},\n  }\n  fmt.Println(\"Original:\", posts)\n  sort.Sort(PSlice(posts))\n  fmt.Println(\"Sorted:\", posts)\n \u002F\u002F Reverse sorting automatically works\n  sort.Sort(sort.Reverse(PSlice(posts)))\n  fmt.Println(\"Reverse sort:\", posts)\n  ...\n}\n",[744,1220,1218],{"__ignoreMap":746},[682,1222,1223],{},[750,1224,755],{"href":1225,"rel":1226},"https:\u002F\u002Fikehakinyemi.pieces.cloud\u002F?p=c21b4f8c07",[754],[682,1228,1229,826],{},[686,1230,825],{},[737,1232,1235],{"className":1233,"code":1234,"language":742},[740],"Original: [{7 I come in peace, comrade! 4.1} {100 No, peace is not an option comrade! 4.7} {13 I preach violence, comrade! 4.5} {-1 I live for violence, comrade 5.5}]\nSorted: [{-1 I live for violence, comrade 5.5} {7 I come in peace, comrade! 4.1} {13 I preach violence, comrade! 4.5} {100 No, peace is not an option comrade! 4.7}]\nReverse sort: [{100 No, peace is not an option comrade! 4.7} {13 I preach violence, comrade! 4.5} {7 I come in peace, comrade! 4.1} {-1 I live for violence, comrade 5.5}]\n",[744,1236,1234],{"__ignoreMap":746},[682,1238,1239,1240,1242,1243,715,1245,772,1247,1249,1250,1253,1254,1256,1257,1260,1261,1264,1265,1268,1269,1271,1272,715,1274,772,1276,1278,1279,1281,1282,1118],{},"That’s a long example, but only implemented the foundational concepts we shared earlier about the ",[744,1241,1050],{}," interface. We implemented ",[744,1244,1104],{},[744,1246,1110],{},[744,1248,1123],{}," for a type, ",[744,1251,1252],{},"PSlice",", which is basically a slice of ",[744,1255,8],{},". With the type methods in place, we can now use the ",[744,1258,1259],{},"sort.Sort"," function to sort the slice, and also make use of the sort.Reverse function to perform reverse sorting on the slice. The ",[744,1262,1263],{},"PSlice(posts)"," expression will adapt the ",[744,1266,1267],{},"[]Pieces"," slice into the ",[744,1270,1252],{}," type with the methods ",[744,1273,1104],{},[744,1275,1110],{},[744,1277,1123],{},". This is possible because ",[744,1280,1267],{}," has the appropriate type signature with ",[744,1283,1252],{},[699,1285,1287],{"id":1286},"conclusion","Conclusion",[682,1289,1290,1291,1294,1295,772,1297,1300,1301,1118],{},"In this tutorial, we covered what reflection and interfaces are in Go. For example, reflection provides a more elegant approach to scrubbing sensitive data before logging it. And as well, interfaces provide the flexibility to implement functionalities based on behaviors expected on a data type. We can now extend these concepts to build complex interfaces by combining one interface with another to form a new interface. The ",[744,1292,1293],{},"ReadCloser"," interface is a typical example of combining two interfaces, ",[744,1296,1181],{},[744,1298,1299],{},"Closer",". The extensibility of these concepts are far beyond this tutorial, so I encourage you to explore more on these concepts. For more about when to use Go in general, check out ",[750,1302,1305],{"href":1303,"rel":1304},"https:\u002F\u002Fpieces.app\u002Fblog\u002Fpython-vs-golang",[754],"this comparison guide",{"title":746,"searchDepth":1307,"depth":1307,"links":1308},2,[1309,1310,1314,1315],{"id":701,"depth":1307,"text":702},{"id":863,"depth":1307,"text":864,"children":1311},[1312,1313],{"id":868,"depth":1173,"text":869},{"id":933,"depth":1173,"text":934},{"id":1204,"depth":1307,"text":1205},{"id":1286,"depth":1307,"text":1287},"Software Development","2023-02-10T00:00:00.000Z","Go offers the Reflection and Interface concepts as part of its collection of features. Let's discuss how to use them properly.",false,"md","https:\u002F\u002Fstorage.googleapis.com\u002Fpieces-marketing-website\u002Fimages\u002Fblog\u002Funderstanding-go-reflection-interfaces\u002Fhero.jpeg","decorative header image",{},"\u002Fblog\u002Funderstanding-go-reflection-interfaces",{"title":673,"description":1318},"blog\u002Funderstanding-go-reflection-interfaces",[1328],"interface; go-a","eCf2N0-Gohppsm8nXUqRwAAnUf2MUodgwOl1KZa5MNg",{"id":1331,"title":674,"body":1332,"description":746,"draft":1319,"extension":1320,"meta":1336,"navigation":32,"path":1337,"photo":1338,"photoAlt":676,"seo":1339,"stem":1340,"__hash__":1341},"authors\u002Fauthors\u002Fikeh-chukwuka-favour.md",{"type":679,"value":1333,"toc":1334},[],{"title":746,"searchDepth":1307,"depth":1307,"links":1335},[],{},"\u002Fauthors\u002Fikeh-chukwuka-favour","https:\u002F\u002Fstorage.googleapis.com\u002Fpieces-marketing-website\u002Fimages\u002Fauthors\u002Fplaceholder.svg",{"title":674,"description":746},"authors\u002Fikeh-chukwuka-favour","p6fwdF2mBNN18doNmfCjFhUy7bvAb47plpZFxZHvvfU",{"left":1343,"top":1343,"width":1344,"height":1344,"rotate":1343,"vFlip":1319,"hFlip":1319,"body":1345},0,24,"\u003Cpath fill=\"currentColor\" d=\"m7.825 13l4.9 4.9q.3.3.288.7t-.313.7q-.3.275-.7.288t-.7-.288l-6.6-6.6q-.15-.15-.213-.325T4.426 12t.063-.375t.212-.325l6.6-6.6q.275-.275.688-.275t.712.275q.3.3.3.713t-.3.712L7.825 11H19q.425 0 .713.288T20 12t-.288.713T19 13z\"\u002F>"]