<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://wiki.extremist.software/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=67.188.9.254</id>
	<title>Noisebridge - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="https://wiki.extremist.software/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=67.188.9.254"/>
	<link rel="alternate" type="text/html" href="https://wiki.extremist.software/wiki/Special:Contributions/67.188.9.254"/>
	<updated>2026-04-06T22:59:02Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.39.13</generator>
	<entry>
		<id>https://wiki.extremist.software/index.php?title=JavaScript/Notes/PrivateProxy&amp;diff=42527</id>
		<title>JavaScript/Notes/PrivateProxy</title>
		<link rel="alternate" type="text/html" href="https://wiki.extremist.software/index.php?title=JavaScript/Notes/PrivateProxy&amp;diff=42527"/>
		<updated>2014-05-18T02:12:56Z</updated>

		<summary type="html">&lt;p&gt;67.188.9.254: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Proxy == &lt;br /&gt;
A proxy is as an interface to something else.&lt;br /&gt;
&lt;br /&gt;
== Private Proxy == &lt;br /&gt;
The private proxy exposes a public interface object. This public interface object delegates some of its responsibility to a private instance.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Structural Pattern:&#039;&#039;&#039; The private and public instances are &amp;lt;dfn&amp;gt;tightly coupled&amp;lt;/dfn&amp;gt;. They share data with each other only within the scope where they are defined. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Usage:&#039;&#039;&#039; Details and complexities of the underlying object must be hidden. By exposing a very limited set of methods, the public interface offers little opportunity to modify and break the objects it produces, while protecting the integrity of the underlying, corresponding private objects.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Example:&#039;&#039;&#039; User wants to be able to interact with &amp;quot;program&amp;quot; objects on a calendar. The &amp;lt;dfn&amp;gt;program&amp;lt;/dfn&amp;gt; can be then modified by the user.&lt;br /&gt;
&lt;br /&gt;
The application handles modification of program objects through a &amp;lt;dfn&amp;gt;ProgramProxy&amp;lt;/dfn&amp;gt;, by calling &amp;lt;dfn&amp;gt;setPhases&amp;lt;/dfn&amp;gt;, &amp;lt;dfn&amp;gt;setCampaigns&amp;lt;/dfn&amp;gt;. The client of the API may call &amp;lt;dfn&amp;gt;buildHTML&amp;lt;/dfn&amp;gt; to generate new HTML for the program or &amp;lt;dfn&amp;gt;toJSON&amp;lt;/dfn&amp;gt; to get a JSON representation of it. &lt;br /&gt;
&lt;br /&gt;
=== Alternatives === &lt;br /&gt;
The popular alternative to this approach is MVC with libraries such as Backbone or YUI app framework. Prefabricated solutions often entail a much larger codebase with less specificity to the design of your particular situation. &lt;br /&gt;
 &lt;br /&gt;
&amp;lt;source lang=&amp;quot;javascript&amp;quot;&amp;gt;&lt;br /&gt;
var Program = function(A) {&lt;br /&gt;
&lt;br /&gt;
  &amp;quot;use strict&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
  var phaseListClassName = &amp;quot;program-phase-list&amp;quot;,&lt;br /&gt;
      phaseClassName = &amp;quot;program-phase&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
  function Program(id, config) {&lt;br /&gt;
    var start = config.startDate,&lt;br /&gt;
        end = config.endDate;&lt;br /&gt;
    this.id = id;&lt;br /&gt;
    this.dateRange = new A.DateRange(start, end);&lt;br /&gt;
    this.phases = config.phases.slice();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  var programs = {},&lt;br /&gt;
      programProxies = {};&lt;br /&gt;
&lt;br /&gt;
  var phaseListElement = document.createElement(&amp;quot;ul&amp;quot;),&lt;br /&gt;
      phaseElement = document.createElement(&amp;quot;li&amp;quot;);&lt;br /&gt;
  phaseListElement.className = phaseListClassName;&lt;br /&gt;
  phaseElement.className = phaseClassName;&lt;br /&gt;
&lt;br /&gt;
  function ProgramProxy(id, config) {&lt;br /&gt;
    this.id = id;&lt;br /&gt;
    this.start = config.startDate;&lt;br /&gt;
    this.displayName = config.name;&lt;br /&gt;
    this.end = config.endDate;&lt;br /&gt;
    programs[id] = new Program(id, config);&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  ProgramProxy.prototype = {&lt;br /&gt;
    setPhases: function(phases) {&lt;br /&gt;
      if(phases &amp;amp;&amp;amp; phases.slice) {&lt;br /&gt;
        programs[this.id].phases = phases.slice();&lt;br /&gt;
      }&lt;br /&gt;
    },&lt;br /&gt;
&lt;br /&gt;
    buildHTML: function() {&lt;br /&gt;
      var program = programs[this.id],&lt;br /&gt;
          html = &amp;quot;&amp;quot;;&lt;br /&gt;
      html += buildPhaseHTML(program);&lt;br /&gt;
      html += buildCampaignHTML(program);&lt;br /&gt;
      return html;&lt;br /&gt;
    }&lt;br /&gt;
  };&lt;br /&gt;
&lt;br /&gt;
  var div = document.createElement(&amp;quot;div&amp;quot;);&lt;br /&gt;
  function buildPhaseHTML(program) {&lt;br /&gt;
    div.innerHTML = &amp;quot;&amp;quot;;&lt;br /&gt;
    var i, li,&lt;br /&gt;
        phases = program.phases,&lt;br /&gt;
        len = phases.length,&lt;br /&gt;
        phaseRationalValue,&lt;br /&gt;
        ul = phaseListElement.cloneNode(false);&lt;br /&gt;
    ul.id = &amp;quot;program-&amp;quot; + program.id;&lt;br /&gt;
    for(i = 0; i &amp;lt; len; i++) {&lt;br /&gt;
      li = phaseElement.cloneNode(false);&lt;br /&gt;
      li.id = &amp;quot;program-&amp;quot;&lt;br /&gt;
            + program.id &lt;br /&gt;
            + &amp;quot;-phase-&amp;quot;&lt;br /&gt;
            + phases[i].name  &lt;br /&gt;
            + &amp;quot;&amp;quot;;&lt;br /&gt;
      li.style.width = &lt;br /&gt;
        getPhaseWidth(phases[i], program.dateRange.duration);&lt;br /&gt;
      ul.appendChild(li);&lt;br /&gt;
    }&lt;br /&gt;
    div.appendChild(ul);&lt;br /&gt;
    return div.innerHTML;&lt;br /&gt;
  }&lt;br /&gt;
 &lt;br /&gt;
  function buildCampaignHTML() {&lt;br /&gt;
    return&amp;quot;&amp;quot;;&lt;br /&gt;
  &amp;quot;&amp;lt;ul&amp;gt;&amp;quot;&lt;br /&gt;
    + &amp;quot;&amp;lt;li&amp;gt;fixme:\u00A0buildCampaignHTML&amp;quot;&lt;br /&gt;
    + &amp;quot;&amp;lt;/ul&amp;gt;&amp;quot;;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  function getPhaseWidth(phase, programDuration) {&lt;br /&gt;
    var phaseDateRange = new A.DateRange(&lt;br /&gt;
      phase.startDate, phase.endDate);&lt;br /&gt;
    var rationalValue = phaseDateRange.duration/programDuration;&lt;br /&gt;
    return (0|100 * rationalValue) + &amp;quot;%&amp;quot;;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  function getOrCreateProgram(config) {&lt;br /&gt;
    return programProxies[config.id] || &lt;br /&gt;
      (programProxies[config.id] = new ProgramProxy(config.id, config));&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  function removeProgram(id) {&lt;br /&gt;
    if(!programs[id]) {&lt;br /&gt;
      throw new ReferenceError(&amp;quot;Program: &amp;quot; &lt;br /&gt;
        + id&lt;br /&gt;
        + &amp;quot; does not exist.&amp;quot; );&lt;br /&gt;
    }&lt;br /&gt;
    delete programs[id];&lt;br /&gt;
    delete programProxies[id];&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  return {&lt;br /&gt;
    getOrCreate: getOrCreateProgram,&lt;br /&gt;
    remove: removeProgram&lt;br /&gt;
  };&lt;br /&gt;
}({&lt;br /&gt;
  DateRange: DateRange // defined elsewhere.&lt;br /&gt;
});&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;code&amp;gt;Program.getOrCreate&amp;lt;/code&amp;gt; returns a &amp;lt;code&amp;gt;ProgramProxy&amp;lt;/code&amp;gt;.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;code&amp;gt;ProgramProxy&amp;lt;/code&amp;gt; has two methods, both of which delegate to &amp;lt;code&amp;gt;Program&amp;lt;/code&amp;gt; instances. &lt;br /&gt;
&lt;br /&gt;
The body of buildHTML:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;javascript&amp;quot;&amp;gt;&lt;br /&gt;
setPhases: function(phases) {&lt;br /&gt;
 if(phases &amp;amp;&amp;amp; phases.slice) {&lt;br /&gt;
    programs[id].phases = phases.slice();&lt;br /&gt;
  }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Because &amp;lt;code&amp;gt;ProgramProxy&amp;lt;/code&amp;gt; and each &amp;lt;code&amp;gt;Program&amp;lt;/code&amp;gt; have the same id, any &amp;lt;code&amp;gt;Program&amp;lt;/code&amp;gt; or &amp;lt;code&amp;gt;ProgramProxy&amp;lt;/code&amp;gt; instance counterpart can access its corresponding counterpart from within any of its instance methods.&lt;br /&gt;
&lt;br /&gt;
This is implemented by both &amp;lt;code&amp;gt;Program&amp;lt;/code&amp;gt; and &amp;lt;code&amp;gt;ProgramProxy&amp;lt;/code&amp;gt; instances being stored in a corresponding object for, keyed by id. &lt;br /&gt;
&lt;br /&gt;
See also: [http://sourcemaking.com/design_patterns/proxy Proxy Design Pattern].&lt;/div&gt;</summary>
		<author><name>67.188.9.254</name></author>
	</entry>
	<entry>
		<id>https://wiki.extremist.software/index.php?title=JavaScript/Notes/PrivateProxy&amp;diff=42526</id>
		<title>JavaScript/Notes/PrivateProxy</title>
		<link rel="alternate" type="text/html" href="https://wiki.extremist.software/index.php?title=JavaScript/Notes/PrivateProxy&amp;diff=42526"/>
		<updated>2014-05-18T02:07:21Z</updated>

		<summary type="html">&lt;p&gt;67.188.9.254: /* Private Proxy */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Proxy == &lt;br /&gt;
A proxy is as an interface to something else.&lt;br /&gt;
&lt;br /&gt;
== Private Proxy == &lt;br /&gt;
The private proxy exposes a public interface object. This public interface object delegates some of its responsibility to a private instance.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Structural Pattern:&#039;&#039;&#039; The private and public instances are &amp;lt;dfn&amp;gt;tightly coupled&amp;lt;/dfn&amp;gt;. They share data with each other only within the scope where they are defined. &lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Usage:&#039;&#039;&#039; Details and complexities of the underlying object must be hidden. By exposing a very limited set of methods, the public interface offers little opportunity to modify and break the objects it produces, while protecting the integrity of the underlying, corresponding private objects.&lt;br /&gt;
&lt;br /&gt;
&#039;&#039;&#039;Example:&#039;&#039;&#039; User wants to be able to interact with &amp;quot;program&amp;quot; objects on a calendar. The &amp;lt;dfn&amp;gt;program&amp;lt;/dfn&amp;gt; can be then modified by the user.&lt;br /&gt;
&lt;br /&gt;
The application handles modification of program objects through a &amp;lt;dfn&amp;gt;ProgramProxy&amp;lt;/dfn&amp;gt;, by calling &amp;lt;dfn&amp;gt;setPhases&amp;lt;/dfn&amp;gt;, &amp;lt;dfn&amp;gt;setCampaigns&amp;lt;/dfn&amp;gt;. The client of the API may call &amp;lt;dfn&amp;gt;buildHTML&amp;lt;/dfn&amp;gt; to generate new HTML for the program or &amp;lt;dfn&amp;gt;toJSON&amp;lt;/dfn&amp;gt; to get a JSON representation of it. &lt;br /&gt;
&lt;br /&gt;
=== Alternatives === &lt;br /&gt;
The popular alternative to this approach is MVC with libraries such as Backbone or YUI app framework. Prefabricated solutions often entail a much larger codebase with less specificity to the design of your particular situation. &lt;br /&gt;
 &lt;br /&gt;
&amp;lt;source lang=&amp;quot;javascript&amp;quot;&amp;gt;&lt;br /&gt;
var Program = function(A) {&lt;br /&gt;
&lt;br /&gt;
  &amp;quot;use strict&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
  var phaseListClassName = &amp;quot;program-phase-list&amp;quot;,&lt;br /&gt;
      phaseClassName = &amp;quot;program-phase&amp;quot;;&lt;br /&gt;
&lt;br /&gt;
  function Program(id, config) {&lt;br /&gt;
    var start = config.startDate,&lt;br /&gt;
        end = config.endDate;&lt;br /&gt;
    this.id = id;&lt;br /&gt;
    this.dateRange = new A.DateRange(start, end);&lt;br /&gt;
    this.phases = config.phases.slice();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  var programs = {},&lt;br /&gt;
      programProxies = {};&lt;br /&gt;
&lt;br /&gt;
  var phaseListElement = document.createElement(&amp;quot;ul&amp;quot;),&lt;br /&gt;
      phaseElement = document.createElement(&amp;quot;li&amp;quot;);&lt;br /&gt;
  phaseListElement.className = phaseListClassName;&lt;br /&gt;
  phaseElement.className = phaseClassName;&lt;br /&gt;
&lt;br /&gt;
  function ProgramProxy(id, config) {&lt;br /&gt;
    this.id = id;&lt;br /&gt;
    this.start = config.startDate;&lt;br /&gt;
    this.displayName = config.name;&lt;br /&gt;
    this.end = config.endDate;&lt;br /&gt;
    programs[id] = new Program(id, config);&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  ProgramProxy.prototype = {&lt;br /&gt;
    setPhases: function(phases) {&lt;br /&gt;
      if(phases &amp;amp;&amp;amp; phases.slice) {&lt;br /&gt;
        programs[this.id].phases = phases.slice();&lt;br /&gt;
      }&lt;br /&gt;
    },&lt;br /&gt;
&lt;br /&gt;
    buildHTML: function() {&lt;br /&gt;
      var program = programs[this.id],&lt;br /&gt;
          html = &amp;quot;&amp;quot;;&lt;br /&gt;
      html += buildPhaseHTML(program);&lt;br /&gt;
      html += buildCampaignHTML(program);&lt;br /&gt;
      return html;&lt;br /&gt;
    }&lt;br /&gt;
  };&lt;br /&gt;
&lt;br /&gt;
  var div = document.createElement(&amp;quot;div&amp;quot;);&lt;br /&gt;
  function buildPhaseHTML(program) {&lt;br /&gt;
    div.innerHTML = &amp;quot;&amp;quot;;&lt;br /&gt;
    var i, li,&lt;br /&gt;
        phases = program.phases,&lt;br /&gt;
        len = phases.length,&lt;br /&gt;
        phaseRationalValue,&lt;br /&gt;
        ul = phaseListElement.cloneNode(false);&lt;br /&gt;
    ul.id = &amp;quot;program-&amp;quot; + program.id;&lt;br /&gt;
    for(i = 0; i &amp;lt; len; i++) {&lt;br /&gt;
      li = phaseElement.cloneNode(false);&lt;br /&gt;
      li.id = &amp;quot;program-&amp;quot;&lt;br /&gt;
            + program.id &lt;br /&gt;
            + &amp;quot;-phase-&amp;quot;&lt;br /&gt;
            + phases[i].name  &lt;br /&gt;
            + &amp;quot;&amp;quot;;&lt;br /&gt;
      li.style.width = &lt;br /&gt;
        getPhaseWidth(phases[i], program.dateRange.duration);&lt;br /&gt;
      ul.appendChild(li);&lt;br /&gt;
    }&lt;br /&gt;
    div.appendChild(ul);&lt;br /&gt;
    return div.innerHTML;&lt;br /&gt;
  }&lt;br /&gt;
 &lt;br /&gt;
  function buildCampaignHTML() {&lt;br /&gt;
    return&amp;quot;&amp;quot;;&lt;br /&gt;
  &amp;quot;&amp;lt;ul&amp;gt;&amp;quot;&lt;br /&gt;
    + &amp;quot;&amp;lt;li&amp;gt;fixme:\u00A0buildCampaignHTML&amp;quot;&lt;br /&gt;
    + &amp;quot;&amp;lt;/ul&amp;gt;&amp;quot;;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  function getPhaseWidth(phase, programDuration) {&lt;br /&gt;
    var phaseDateRange = new A.DateRange(&lt;br /&gt;
      phase.startDate, phase.endDate);&lt;br /&gt;
    var rationalValue = phaseDateRange.duration/programDuration;&lt;br /&gt;
    return (0|100 * rationalValue) + &amp;quot;%&amp;quot;;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  function getOrCreateProgram(config) {&lt;br /&gt;
    return programProxies[config.id] || &lt;br /&gt;
      (programProxies[config.id] = new ProgramProxy(config.id, config));&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  function removeProgram(id) {&lt;br /&gt;
    if(!programs[id]) {&lt;br /&gt;
      throw new ReferenceError(&amp;quot;Program: &amp;quot; &lt;br /&gt;
        + id&lt;br /&gt;
        + &amp;quot; does not exist.&amp;quot; );&lt;br /&gt;
    }&lt;br /&gt;
    delete programs[id];&lt;br /&gt;
    delete programProxies[id];&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  return {&lt;br /&gt;
    getOrCreate: getOrCreateProgram,&lt;br /&gt;
    remove: removeProgram&lt;br /&gt;
  };&lt;br /&gt;
}({&lt;br /&gt;
  DateRange: DateRange // defined elsewhere.&lt;br /&gt;
});&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
`Program.getOrCreate` returns a `ProgramProxy`.&lt;br /&gt;
&lt;br /&gt;
`ProgramProxy` has two methods, both of which delegate to `Program` instances. &lt;br /&gt;
&lt;br /&gt;
The body of buildHTML&lt;br /&gt;
&amp;lt;source lang=&amp;quot;javascript&amp;quot;&amp;gt;&lt;br /&gt;
setPhases: function(phases) {&lt;br /&gt;
 if(phases &amp;amp;&amp;amp; phases.slice) {&lt;br /&gt;
    programs[id].phases = phases.slice();&lt;br /&gt;
  }&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This is possible because `ProgramProxy` and each `Program` have the same id. Each are stored in one of two objects, keyed by their id. See also: [http://sourcemaking.com/design_patterns/proxy Proxy Design Pattern].&lt;/div&gt;</summary>
		<author><name>67.188.9.254</name></author>
	</entry>
</feed>