.NET与Vue之间通过[FromForm]进行API通信

huangapple go评论53阅读模式
英文:

.NET & Vue API communication through [FromForm]

问题

以下是您要翻译的代码部分:

I'm trying to send a list of object in which contains IFormFile.

Here are my object :

public class ImageGalleryDto
{
    public Guid? PageId { get; set; }
    public int? Order { get; set; }
    public IFormFile? Image { get; set; }
}

My endpoint in .net core : 

public async Task<EndpointResult<object>> UpdateImageGallery([FromForm] List<ImageGalleryDto> imageGalleryDto)


My object in vue is exactly same as with this model. And I'm trying to send like this in vue.js

const formData = new FormData();
formData.append("imageGalleryDto", pushToApi);

this.updateImageGallery(formData).then((res) => {....}

Unfortunately, in the controller, the list is empty when it is called.
英文:

I'm trying to send a list of object in which contains IFormFile.

Here are my object :

public class ImageGalleryDto
{
    public Guid? PageId { get; set; }
    public int? Order { get; set; }
    public IFormFile? Image { get; set; }
}

My endpoint in .net core :

public async Task<EndpointResult<object>> UpdateImageGallery([FromForm] List<ImageGalleryDto> imageGalleryDto)

My object in vue is exactly same as with this model. And I'm trying to send like this in vue.js

const formData = new FormData();
formData.append("imageGalleryDto", pushToApi);

this.updateImageGallery(formData).then((res) => {....}

Unfortunately, in the controller, the list is empty when it is called.

答案1

得分: 1

根据您的描述,似乎与您的表单数据有问题,表单数据应该如下所示,然后ASP.NET Core模型绑定将自动将数据绑定到Web API控制器内的模型。

const formData = new FormData();
this.images.forEach((image, index) => {
    formData.append(`imageGalleryDto[${index}].pageId`, image.pageId);
    formData.append(`imageGalleryDto[${index}].order`, image.order);
    formData.append(`imageGalleryDto[${index}].image`, image.image);
});

详细示例如下:

由于您有vue.js标签,我使用vue.js示例。

客户端:

<div id="app">
    <image-upload-form></image-upload-form>
</div>

<script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.min.js"></script>
<script>
    Vue.component('image-upload-form', {
        template: `
        <div>
          <form @submit.prevent="uploadImages" enctype="multipart/form-data">
            <div v-for="(image, index) in images" :key="index">
              <input type="text" v-model="image.pageId" :name="'images[index].pageId'" placeholder="Page ID"/>
              <input type="number" v-model="image.order" :name="'images[index].order'" placeholder="Order"/>
              <input type="file" ref="file" :name="'images[index].image'" @change="onFileChange(index,$event)" />
            </div>
            <button type="submit">Upload Images</button>
          </form>
        </div>
      `,
        data() {
            return {
                images: [{ pageId: '', order: '', image: null }, { pageId: '', order: '', image: null }]
            };
        },
        methods: {
            onFileChange(index, event) {
                    this.images[index].image = event.target.files[0];
            },
            async uploadImages() {
                const formData = new FormData();
                this.images.forEach((image, index) => {
                    formData.append(`imageGalleryDto[${index}].pageId`, image.pageId);
                    formData.append(`imageGalleryDto[${index}].order`, image.order);
                    formData.append(`imageGalleryDto[${index}].image`, image.image);
                });

                try {
                    const response = await fetch('https://localhost:7204/api/values/upload', {
                        method: 'POST',
                        body: formData
                    });

                    if (response.ok) {
                        console.log('Images uploaded successfully');
                    } else {
                        console.error('Failed to upload images');
                    }
                } catch (error) {
                    console.error('Error uploading images', error);
                }
            }
        }
    });

    new Vue({
        el: '#app'
    });
</script>

后端:

[Route("api/[controller]")]
[ApiController]
public class ValuesController : ControllerBase
{

    [HttpPost("upload")]
    public async Task<IActionResult> UploadImages([FromForm] List<ImageGalleryDto> imageGalleryDto)
    {
        // 对imageGalleryDto对象执行某些操作
        return new JsonResult("OK");
    }
}

结果:

.NET与Vue之间通过[FromForm]进行API通信

英文:

According to your description, it looks like there is something wrong with your formdata, the formdata should like below, then the asp.net core model binding will auto bind the data to the model inside the web api controller.

                const formData = new FormData();
this.images.forEach((image, index) =&gt; {
formData.append(`imageGalleryDto[${index}].pageId`, image.pageId);
formData.append(`imageGalleryDto[${index}].order`, image.order);
formData.append(`imageGalleryDto[${index}].image`, image.image);
});

The details example like below:

Since you have vue.js tag, I use vue.js example

Client:

&lt;div id=&quot;app&quot;&gt;
&lt;image-upload-form&gt;&lt;/image-upload-form&gt;
&lt;/div&gt;
&lt;script src=&quot;https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.min.js&quot;&gt;&lt;/script&gt;
&lt;script&gt;
Vue.component(&#39;image-upload-form&#39;, {
template: `
&lt;div&gt;
&lt;form @submit.prevent=&quot;uploadImages&quot; enctype=&quot;multipart/form-data&quot;&gt;
&lt;div v-for=&quot;(image, index) in images&quot; :key=&quot;index&quot;&gt;
&lt;input type=&quot;text&quot; v-model=&quot;image.pageId&quot; :name=&quot;&#39;images[index].pageId&#39;&quot; placeholder=&quot;Page ID&quot;/&gt;
&lt;input type=&quot;number&quot; v-model=&quot;image.order&quot; :name=&quot;&#39;images[index].order&#39;&quot; placeholder=&quot;Order&quot;/&gt;
&lt;input type=&quot;file&quot; ref=&quot;file&quot; :name=&quot;&#39;images[index].image&#39;&quot; @change=&quot;onFileChange(index,$event)&quot; /&gt;
&lt;/div&gt;
&lt;button type=&quot;submit&quot;&gt;Upload Images&lt;/button&gt;
&lt;/form&gt;
&lt;/div&gt;
`,
data() {
return {
images: [{ pageId: &#39;&#39;, order: &#39;&#39;, image: null }, { pageId: &#39;&#39;, order: &#39;&#39;, image: null }]
};
},
methods: {
onFileChange(index, event) {
this.images[index].image = event.target.files[0];
},
async uploadImages() {
const formData = new FormData();
this.images.forEach((image, index) =&gt; {
formData.append(`imageGalleryDto[${index}].pageId`, image.pageId);
formData.append(`imageGalleryDto[${index}].order`, image.order);
formData.append(`imageGalleryDto[${index}].image`, image.image);
});
try {
const response = await fetch(&#39;https://localhost:7204/api/values/upload&#39;, {
method: &#39;POST&#39;,
body: formData
});
if (response.ok) {
console.log(&#39;Images uploaded successfully&#39;);
} else {
console.error(&#39;Failed to upload images&#39;);
}
} catch (error) {
console.error(&#39;Error uploading images&#39;, error);
}
}
}
});
new Vue({
el: &#39;#app&#39;
});
&lt;/script&gt;

Backend:

[Route(&quot;api/[controller]&quot;)]
[ApiController]
public class ValuesController : ControllerBase
{
[HttpPost(&quot;upload&quot;)]
public async Task&lt;IActionResult&gt; UploadImages([FromForm] List&lt;ImageGalleryDto&gt; imageGalleryDto)
{
// Do something with the imageGalleryDtos object
return new JsonResult(&quot;OK&quot;);
}

Result:

.NET与Vue之间通过[FromForm]进行API通信

huangapple
  • 本文由 发表于 2023年2月14日 04:18:05
  • 转载请务必保留本文链接:https://go.coder-hub.com/75440777.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定