vuejs / docs

📄 Documentation for Vue 3
https://vuejs.org
Other
2.94k stars 4.47k forks source link

Example of how composition is used in CDN version of Vue 3 #786

Closed macdevign closed 2 years ago

macdevign commented 3 years ago

Is there a code example of how composition is used in CDN version of vue 3 ? If not, anyone can provide a working sample ? thank

skirtles-code commented 3 years ago

I'm not sure what you mean. It should be much the same as using it with ESM/SFC, but with the composition functions exposed via the global Vue. e.g.:

const { ref } = Vue
woodz- commented 3 years ago

Aloha, I guess @macdevign means a sample on how to include vv3 into a html file via the <script> tag. Since one of the very first steps in the vv2 doc is:

<!-- development version, includes helpful console warnings -->
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>

it is missing (not stated) on the beginning of the vv3 doc. If users step in to vv3 without the knowledge of vv2, like I did, they need to improperly dig into.

bencodezen commented 3 years ago

Hi @macdevign anad @woodz-!

The CDN installation method is mentioned here: https://v3.vuejs.org/guide/installation.html#cdn

If we were to use the CDN method, the page would look something like:

<html>
  <body>
    <div id="app">
      <h1>{{ count }}</h1>
      <button @click="increment">Increment</button>
    </div>
    <script src="https://unpkg.com/vue@next"></script>
    <script>
      const { ref, createApp } = Vue
      createApp({
        setup() {
          const count = ref(0)

          const increment = () => {
            count.value++
          }

          return {
            count, 
            increment
          }
        }
      }.mount('#app')
    </script>  
  </body>
</html>

Hope this helps in the meantime while we document a clear path for users using the CDN.

macdevign commented 3 years ago

Thank for everyone's help here.

Ben, thank for that sample. I find CDN version is very useful as not every project needs transpilation, and hence thank for adding doc for it. For example, I using CDN vue.js in Keyboard maestro's Custom HTML Prompt action (it basically a webview wrapper that can accept html file) that can create sophisticated macro application. https://wiki.keyboardmaestro.com/action/Custom_HTML_Prompt

NataliaTepluhina commented 2 years ago

Closing as we have the example with API set to Composition API + HTML

murugappanrm commented 2 years ago

Hi,

I am trying to use the vue cdn to develop an app. The problem i have is I want to load the index page with the main vue component. Then i want to dynamically load sub-components from external js files and inject into this main vue component in the index.html. Let me give you an example: The index page loads a vuejs side bar menu. One selecting a menu, the related component is loaded as page details and injected. That way the main page and it sidebar remains and only the details contents get loaded thereby removing page reload. I could not get much help on this anywhere. Has anyone done this?

Please help

ijazpakhtun commented 2 years ago

do we have a way to write compistion api script setup with cdn like this?

<template> {{message}} </template>

``

murugappanrm commented 2 years ago

Hi @ijazpakhtun , Its weird, no one seems to be able to help with our needs. Either it cannot be done or competency is lacking in this areas. All we get is "why dont you use the CLI... " sigh! If CDN is not to be used then why for heaven sake provide it, is my question?

skirtles-code commented 2 years ago

@ijazpakhtun @murugappanrm This GitHub issues list is for reporting problems with the docs. You won't get replies to help requests.

If you need help with a problem then please ask on the Vue Land Discord or StackOverflow.

ijazpakhtun commented 2 years ago

@murugappanrm , consider when you don't use single page app or the full features of Vue but you use vue as a library, like we can use use vue instead of jquery and take advantages of vue rather than using vanila js or jquery etc..

murugappanrm commented 2 years ago

@skirtles-code , this is about the docs. Its not about the software. There is no clear examples or explanations on the CDN option. There are not much tutorials in YouTube either. Everyone is on CLI and no one seem to know the CDN. I was sarcastically told that if i have complains about doc i should help to update the docs. Sigh!

ijazpakhtun commented 2 years ago

@murugappanrm you are right there should be some documentation about the script setup using CDN but if they don't support it, this should be cleared somewhere that we no longer support this. Everyone use case is different so in some projects you will use CLI but in some other you may use CDN. Thanks

murugappanrm commented 2 years ago

@bencodezen @ijazpakhtun

I have been royally insulted by people on my reasons for using the CDN option by people who masquerade as "super brains" instead of syaing " I dont know". They seem to forget to "listen to their customers". As business solution developers, we learn from our customers. @ijazpakhtun we are now also venturing into Alpinejs, Astro and Tailwind which seem to be better suited platforms for our needs. We are getting better results at a faster pace. For full blown webstack we still use Vue CLI and Quasar Vite.

bencodezen commented 2 years ago

Hi @murugappanrm. Sorry to hear about your frustration with this.

As you've seen discussed, script setup currently requires a compiler to work, so to my knowledge, this would not apply to CDN usage of Vue. We shall iterate on the docs to make this clearer for people, but let's track this in a new issue.

Would you be open to filing a new issue in the docs repo to bring this up so you can be credited for this work? Feel free to tag me in it when you do.

murugappanrm commented 2 years ago

@bencodezen and @ijazpakhtun i have raised a separate issue on this https://github.com/vuejs/docs/issues/1953. Thank you.

smallFledging commented 1 year ago

@bencodezen and @ijazpakhtun i have raised a separate issue on this #1953. Thank you.

Hello, this is not from vue but here is a great sandbox example using CDN I'm using. https://codesandbox.io/u/Backpackstudio If you originally used vue 2 you can swap myscript.js for main.js and then use at the end of the index.html body. Then change app.mount('#vuetest') to app.mount('#app')

Here is an example of using vue 3 composition for vue 2 users https://vuejsdevelopers.com/2020/03/16/vue-js-tutorial/

murugappanrm commented 1 year ago

@smallFledging

Thank you so much for the example. It was great help. One question still remains unanswered,

With the code, i am loading the vue component at the div with the speicfied id. The problem is the i would like to load components (in myscripts.js) with template html. That way the html contents would change just like components in vue/cli.

What i am trying to do is to embed vue js into codeigniter(php) and reduce the need to have a separate front-end vuejs app and back-end headless cms.

smallFledging commented 1 year ago

Hello, I'm glad it helped! Do you specifically need to have your components as templates? I think vuex could be helpful for you as you can have your data separately to the html. So all your data is set in your store which you can refer to when you're using your app or any components. With vuex you can have a mounted function where you can set the data to your request, so if your data is empty, it will not show the element.

I wonder if using vue 2 would be more useful in your position instead with vuex 3 https://techformist.com/use-vue-from-url-simple-app/ In this way you can have html files where you write your template in backticks

If you want to use vue 3, you will have to rejig your myscripts file so it uses imports, or potentially just keep app inside index.html with imported components instead. you have your component written as testComponent.html for example, you can then import it into your index file like this https://vuejs.org/guide/components/registration.html#global-registration

murugappanrm commented 1 year ago

@smallFledging

If you want to use vue 3, you will have to rejig your myscripts file so it uses imports, or potentially just keep app inside index.html with imported components instead. you have your component written as testComponent.html for example, you can then import it into your index file like this https://vuejs.org/guide/components/registration.html#global-registration

This is what i want to do. I am a newbie to vuejs. I have done lots of tutorials and quite familiar now with CLI version. I am having lots of trouble with using the CDN option and the documentation is not helping me much and so does the internet. Could i seek you assistance in this? One example will get me the understanding and also onward.

smallFledging commented 1 year ago

Hello, I've had a play around but here is a vue 3 example with CDN. I also agree there is a lack of documentation for Vue 3 but hopefully this helps! so in my public folder I have index.html and main.js, then a separate folder called components with test.js inside it

Test component:

const test = { template: <div @click='testClick'>Test template

{{test}}
    <div>{{abc}}</div>

`,
props: {
    abc: {
        type: String,
        required: true,
    }
},
data() {
    return {
        test: 'ah hellooo'
    }
},
methods: {
    testClick() {
        console.log('this is a test click from component')
    }
},
mounted() {

},

} export default test;`

Inside index.html use the normal vue script tag in the head and inside body have id='app' but then I have a div <div @click='test'>test

and then in main.js

`import Test from './components/test.js' const {createStore} = Vuex; const store = createStore({ state () { return { test: 0 } }, mutations: { increment (state) { state.test++ } } })

const { createApp } = Vue;

createApp({ data() { return { message: 'Hello Vue!', } }, mounted() { {

}

}, computed: { testComputed() { return this.$store.state.test } }, methods: { test() { console.log('state test', this.$store.state.test) console.log('message', this.message) } } ,

}).component('test', Test).use(store).mount("#app");`

you can chain component on app but using .component('test', Test).component('test2', Test2) etc

Sorry, it hasn't formatted well because of the backticks in the test component but you can see it ends just before props

murugappanrm commented 1 year ago

@smallFledging

I tried creating the code but i must be making mistakes. It didnt work. Could you send me the code to murugappan_rm51@yahoo.com? Appreciate it.

smallFledging commented 1 year ago

Hello, here is a codesandbox,, if you go to console you can see it logs test from state: https://codesandbox.io/s/compassionate-colden-tvt4tu?file=/components/test.js and increments it from test click as it dispatches the action

murugappanrm commented 1 year ago

@smallFledging

You are good man, sir. Your code is exactly what i was looking for. Now i can expand on this one to use Pinia and Composition API. Please put this into the vue.js documentation. It will help a lot of people, especially people who intend to transition.

Thank you so much once again.

doglex commented 1 year ago

a demo

<!DOCTYPE html>
<html>
<head>
  <script src="https://unpkg.com/vue@3/dist/vue.global.js"></script>
  <style>
  .logs {
    background-color: black;
    color:white;
    height:90vh;
    overflow-x: hidden;
    overflow-y: auto;
    text-align: left;
    padding-left:10px;
  }
  </style>
</head>

<body>

<h1>Server Logs:</h1>
<div id="app">
  <div class="logs" ref="refLogs">
    <p v-for="line in lines" :style="{color: line.toLowerCase().indexOf('10') > -1 ? 'red' : 'yellow' }">
      {{line}}
    </p>
  </div>
</div>

<script>
const { createApp, ref, onMounted } = Vue
createApp({
setup() {
  const lines = ref([])
  const refLogs  = ref(null)
  onMounted(()=>{
    const source =  new EventSource("http://localhost:8000/stream-logs")
    source.onmessage = (event) => {
      lines.value.push(event.data)
      // scroll to bottom
      refLogs.value.scrollTop = refLogs.value.scrollHeight
      // keep max queue size
      if (lines.value.length > 10000) {
        lines.value.shift()
      }
    }
  })
  return {
    lines,
    refLogs
  }
}
}).mount('#app')
</script>

</body>
</html>