CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/maven-com-github-binarywang--weixin-java-mp

Comprehensive Java SDK for WeChat Official Account development with complete API coverage for user management, messaging, materials, menus, and WeChat platform features.

Pending
Overview
Eval results
Files

material-management.mddocs/

Material Management

Upload, download, and manage permanent and temporary media materials for WeChat Official Account content.

Material Service Interface

interface WxMpMaterialService {
  // Temporary material operations
  WxMediaUploadResult mediaUpload(String mediaType, String fileType, InputStream inputStream) throws WxErrorException;
  WxMediaUploadResult mediaUpload(String mediaType, String fileType, File file) throws WxErrorException;
  File mediaDownload(String mediaId) throws WxErrorException;
  InputStream mediaDownload(String mediaId, boolean buffered) throws WxErrorException;
  
  // Permanent material operations
  WxMpMaterialUploadResult materialFileUpload(String mediaType, String fileName, InputStream inputStream) throws WxErrorException;
  WxMpMaterialUploadResult materialFileUpload(String mediaType, File file) throws WxErrorException;
  WxMpMaterialNewsUploadResult materialNewsUpload(WxMpMaterialNews news) throws WxErrorException;
  WxMpMaterialVideoInfoResult materialVideoInfo(String mediaId) throws WxErrorException;
  WxMpMaterialNews materialNewsInfo(String mediaId) throws WxErrorException;
  InputStream materialImageOrVoiceDownload(String mediaId) throws WxErrorException;
  WxMpMaterialFileBatchGetResult materialFileBatchGet(String type, int offset, int count) throws WxErrorException;
  WxMpMaterialNewsBatchGetResult materialNewsBatchGet(int offset, int count) throws WxErrorException;
  boolean materialDelete(String mediaId) throws WxErrorException;
  WxMpMaterialCountResult materialCount() throws WxErrorException;
  WxMpMaterialNewsUploadResult materialNewsUpdate(WxMpMaterialArticleUpdate wxMpMaterialArticleUpdate) throws WxErrorException;
  
  // Image upload for articles
  WxMpMaterialUploadResult materialImgUpload(File file) throws WxErrorException;
  WxMpMaterialUploadResult materialImgUpload(InputStream inputStream, String fileName) throws WxErrorException;
}

Data Models

Upload Results

class WxMediaUploadResult implements Serializable {
  private String type;
  private String mediaId;
  private long createdAt;
  
  public String getType();
  public void setType(String type);
  public String getMediaId();
  public void setMediaId(String mediaId);
  public long getCreatedAt();
  public void setCreatedAt(long createdAt);
}

class WxMpMaterialUploadResult implements Serializable {
  private String mediaId;
  private String url;
  
  public String getMediaId();
  public void setMediaId(String mediaId);
  public String getUrl();
  public void setUrl(String url);
}

class WxMpMaterialNewsUploadResult extends WxMpMaterialUploadResult {
  // Inherits mediaId and url fields
}

News Materials

class WxMpMaterialNews implements Serializable {
  private List<WxMpMaterialNews.WxMpMaterialNewsArticle> articles;
  
  public List<WxMpMaterialNewsArticle> getArticles();
  public void setArticles(List<WxMpMaterialNewsArticle> articles);
  public void addArticle(WxMpMaterialNewsArticle article);
  
  public static class WxMpMaterialNewsArticle implements Serializable {
    private String title;
    private String author;
    private String digest;
    private String content;
    private String contentSourceUrl;
    private String thumbMediaId;
    private Integer showCoverPic;
    private Integer needOpenComment;
    private Integer onlyFansCanComment;
    
    public String getTitle();
    public void setTitle(String title);
    public String getAuthor();
    public void setAuthor(String author);
    public String getDigest();
    public void setDigest(String digest);
    public String getContent();
    public void setContent(String content);
    public String getContentSourceUrl();
    public void setContentSourceUrl(String contentSourceUrl);
    public String getThumbMediaId();
    public void setThumbMediaId(String thumbMediaId);
    public Integer getShowCoverPic();
    public void setShowCoverPic(Integer showCoverPic);
    public Integer getNeedOpenComment();
    public void setNeedOpenComment(Integer needOpenComment);
    public Integer getOnlyFansCanComment();
    public void setOnlyFansCanComment(Integer onlyFansCanComment);
  }
}

Video Information

class WxMpMaterialVideoInfoResult implements Serializable {
  private String title;
  private String description;
  private String downUrl;
  
  public String getTitle();
  public void setTitle(String title);
  public String getDescription();
  public void setDescription(String description);
  public String getDownUrl();
  public void setDownUrl(String downUrl);
}

Batch Get Results

class WxMpMaterialFileBatchGetResult implements Serializable {
  private int totalCount;
  private int itemCount;
  private List<WxMpMaterialFileBatchGetResult.WxMpMaterialFileBatchGetNewsItem> items;
  
  public int getTotalCount();
  public void setTotalCount(int totalCount);
  public int getItemCount();
  public void setItemCount(int itemCount);
  public List<WxMpMaterialFileBatchGetNewsItem> getItems();
  public void setItems(List<WxMpMaterialFileBatchGetNewsItem> items);
  
  public static class WxMpMaterialFileBatchGetNewsItem implements Serializable {
    private String mediaId;
    private String name;
    private long updateTime;
    private String url;
    
    public String getMediaId();
    public void setMediaId(String mediaId);
    public String getName();
    public void setName(String name);
    public long getUpdateTime();
    public void setUpdateTime(long updateTime);
    public String getUrl();
    public void setUrl(String url);
  }
}

class WxMpMaterialNewsBatchGetResult implements Serializable {
  private int totalCount;
  private int itemCount;
  private List<WxMpMaterialNewsBatchGetResult.WxMpMaterialNewsBatchGetNewsItem> items;
  
  public int getTotalCount();
  public void setTotalCount(int totalCount);
  public int getItemCount();
  public void setItemCount(int itemCount);
  public List<WxMpMaterialNewsBatchGetNewsItem> getItems();
  public void setItems(List<WxMpMaterialNewsBatchGetNewsItem> items);
  
  public static class WxMpMaterialNewsBatchGetNewsItem implements Serializable {
    private String mediaId;
    private WxMpMaterialNews content;
    private long updateTime;
    
    public String getMediaId();
    public void setMediaId(String mediaId);
    public WxMpMaterialNews getContent();
    public void setContent(WxMpMaterialNews content);
    public long getUpdateTime();
    public void setUpdateTime(long updateTime);
  }
}

Material Count

class WxMpMaterialCountResult implements Serializable {
  private int voiceCount;
  private int videoCount;
  private int imageCount;
  private int newsCount;
  
  public int getVoiceCount();
  public void setVoiceCount(int voiceCount);
  public int getVideoCount();
  public void setVideoCount(int videoCount);
  public int getImageCount();
  public void setImageCount(int imageCount);
  public int getNewsCount();
  public void setNewsCount(int newsCount);
}

Article Update

class WxMpMaterialArticleUpdate implements Serializable {
  private String mediaId;
  private int index;
  private WxMpMaterialNews.WxMpMaterialNewsArticle articles;
  
  public String getMediaId();
  public void setMediaId(String mediaId);
  public int getIndex();
  public void setIndex(int index);
  public WxMpMaterialNews.WxMpMaterialNewsArticle getArticles();
  public void setArticles(WxMpMaterialNews.WxMpMaterialNewsArticle articles);
}

Media Types

// Common media type constants
public static final String MEDIA_TYPE_IMAGE = "image";
public static final String MEDIA_TYPE_VOICE = "voice";
public static final String MEDIA_TYPE_VIDEO = "video";
public static final String MEDIA_TYPE_THUMB = "thumb";
public static final String MEDIA_TYPE_NEWS = "news";

Draft and Publishing Services

interface WxMpDraftService {
  // Draft operations
  WxMpDraftUploadResult addDraft(WxMpDraftArticles articles) throws WxErrorException;
  WxMpDraftArticles getDraft(String mediaId) throws WxErrorException;
  void delDraft(String mediaId) throws WxErrorException;
  WxMpDraftUpdateResult updateDraft(String mediaId, int index, WxMpDraftArticles articles) throws WxErrorException;
  WxMpDraftListResult getDraftList(int offset, int count, int noContent) throws WxErrorException;
  int getDraftTotalCount() throws WxErrorException;
}

interface WxMpFreePublishService {
  // Free publishing operations
  WxMpFreePublishResult submitPublish(String mediaId) throws WxErrorException;
  WxMpFreePublishStatus getPublishStatus(String publishId) throws WxErrorException;
  void deletePublish(String articleId, int index) throws WxErrorException;
  WxMpFreePublishArticles getPublishArticle(String articleId) throws WxErrorException;
  WxMpFreePublishList getPublishList(int offset, int count, int noContent) throws WxErrorException;
}

Usage Examples

Upload Temporary Media

// Upload image file
File imageFile = new File("path/to/image.jpg");
WxMediaUploadResult result = wxService.getMaterialService()
    .mediaUpload(WxConsts.MediaFileType.IMAGE, "image", imageFile);

String mediaId = result.getMediaId();
System.out.println("Uploaded media ID: " + mediaId);

// Upload with InputStream
InputStream inputStream = new FileInputStream("path/to/voice.mp3");
WxMediaUploadResult voiceResult = wxService.getMaterialService()
    .mediaUpload(WxConsts.MediaFileType.VOICE, "voice", inputStream);

Download Temporary Media

// Download as File
String mediaId = "media_id_from_upload";
File downloadedFile = wxService.getMaterialService().mediaDownload(mediaId);

// Download as InputStream
InputStream downloadStream = wxService.getMaterialService()
    .mediaDownload(mediaId, true);

// Save to local file
try (FileOutputStream fos = new FileOutputStream("downloaded_media.jpg")) {
    byte[] buffer = new byte[1024];
    int bytesRead;
    while ((bytesRead = downloadStream.read(buffer)) != -1) {
        fos.write(buffer, 0, bytesRead);
    }
}

Upload Permanent Materials

// Upload permanent image
File permanentImage = new File("path/to/permanent_image.jpg");
WxMpMaterialUploadResult permanentResult = wxService.getMaterialService()
    .materialFileUpload(WxConsts.MediaFileType.IMAGE, permanentImage);

String permanentMediaId = permanentResult.getMediaId();
String imageUrl = permanentResult.getUrl();

// Upload permanent video with metadata
File videoFile = new File("path/to/video.mp4");
WxMpMaterialUploadResult videoResult = wxService.getMaterialService()
    .materialFileUpload(WxConsts.MediaFileType.VIDEO, videoFile);

Create and Upload News Articles

// Create news article
WxMpMaterialNews news = new WxMpMaterialNews();
List<WxMpMaterialNews.WxMpMaterialNewsArticle> articles = new ArrayList<>();

// Create first article
WxMpMaterialNews.WxMpMaterialNewsArticle article1 = 
    new WxMpMaterialNews.WxMpMaterialNewsArticle();
article1.setTitle("Article Title");
article1.setAuthor("Author Name");
article1.setDigest("Article summary");
article1.setContent("<p>Article content in HTML</p>");
article1.setContentSourceUrl("https://example.com/source");
article1.setThumbMediaId("thumb_media_id");
article1.setShowCoverPic(1);
article1.setNeedOpenComment(1);
article1.setOnlyFansCanComment(0);
articles.add(article1);

// Add more articles if needed
WxMpMaterialNews.WxMpMaterialNewsArticle article2 = 
    new WxMpMaterialNews.WxMpMaterialNewsArticle();
article2.setTitle("Second Article");
article2.setAuthor("Author Name");
article2.setDigest("Second article summary");
article2.setContent("<p>Second article content</p>");
article2.setThumbMediaId("thumb_media_id_2");
articles.add(article2);

news.setArticles(articles);

// Upload news
WxMpMaterialNewsUploadResult newsResult = wxService.getMaterialService()
    .materialNewsUpload(news);
String newsMediaId = newsResult.getMediaId();

Update News Articles

// Update specific article in news
WxMpMaterialArticleUpdate update = new WxMpMaterialArticleUpdate();
update.setMediaId("news_media_id");
update.setIndex(0); // Update first article (0-based index)

WxMpMaterialNews.WxMpMaterialNewsArticle updatedArticle = 
    new WxMpMaterialNews.WxMpMaterialNewsArticle();
updatedArticle.setTitle("Updated Title");
updatedArticle.setContent("<p>Updated content</p>");
updatedArticle.setThumbMediaId("updated_thumb_media_id");

update.setArticles(updatedArticle);

WxMpMaterialNewsUploadResult updateResult = wxService.getMaterialService()
    .materialNewsUpdate(update);

Get Material Information

// Get video information
WxMpMaterialVideoInfoResult videoInfo = wxService.getMaterialService()
    .materialVideoInfo("video_media_id");
System.out.println("Video title: " + videoInfo.getTitle());
System.out.println("Video description: " + videoInfo.getDescription());

// Get news information
WxMpMaterialNews newsInfo = wxService.getMaterialService()
    .materialNewsInfo("news_media_id");
List<WxMpMaterialNews.WxMpMaterialNewsArticle> articles = newsInfo.getArticles();
for (WxMpMaterialNews.WxMpMaterialNewsArticle article : articles) {
    System.out.println("Article: " + article.getTitle());
}

Download Permanent Materials

// Download permanent image or voice
InputStream permanentStream = wxService.getMaterialService()
    .materialImageOrVoiceDownload("permanent_media_id");

// Save to file
try (FileOutputStream fos = new FileOutputStream("permanent_material.jpg")) {
    byte[] buffer = new byte[1024];
    int bytesRead;
    while ((bytesRead = permanentStream.read(buffer)) != -1) {
        fos.write(buffer, 0, bytesRead);
    }
}

Batch Get Materials

// Get permanent images in batches
WxMpMaterialFileBatchGetResult imageList = wxService.getMaterialService()
    .materialFileBatchGet(WxConsts.MediaFileType.IMAGE, 0, 20);

System.out.println("Total images: " + imageList.getTotalCount());
for (WxMpMaterialFileBatchGetResult.WxMpMaterialFileBatchGetNewsItem item : imageList.getItems()) {
    System.out.println("Image: " + item.getName() + " - " + item.getMediaId());
}

// Get news articles in batches
WxMpMaterialNewsBatchGetResult newsList = wxService.getMaterialService()
    .materialNewsBatchGet(0, 20);

System.out.println("Total news: " + newsList.getTotalCount());
for (WxMpMaterialNewsBatchGetResult.WxMpMaterialNewsBatchGetNewsItem item : newsList.getItems()) {
    System.out.println("News: " + item.getMediaId());
    WxMpMaterialNews content = item.getContent();
    for (WxMpMaterialNews.WxMpMaterialNewsArticle article : content.getArticles()) {
        System.out.println("  Article: " + article.getTitle());
    }
}

Get Material Count

// Get count of all material types
WxMpMaterialCountResult count = wxService.getMaterialService().materialCount();
System.out.println("Images: " + count.getImageCount());
System.out.println("Videos: " + count.getVideoCount());
System.out.println("Voices: " + count.getVoiceCount());
System.out.println("News: " + count.getNewsCount());

Delete Materials

// Delete permanent material
boolean deleted = wxService.getMaterialService().materialDelete("media_id_to_delete");
if (deleted) {
    System.out.println("Material deleted successfully");
} else {
    System.out.println("Failed to delete material");
}

Upload Images for Articles

// Upload image for use in article content
File articleImage = new File("path/to/article_image.jpg");
WxMpMaterialUploadResult articleImgResult = wxService.getMaterialService()
    .materialImgUpload(articleImage);

String articleImageUrl = articleImgResult.getUrl();

// Use the URL in article content
String articleContent = "<p>Article text</p>" +
    "<img src=\"" + articleImageUrl + "\" alt=\"Article Image\">" +
    "<p>More article text</p>";

Batch Operations

// Get all permanent materials with pagination
List<WxMpMaterialFileBatchGetResult.WxMpMaterialFileBatchGetNewsItem> allImages = new ArrayList<>();
int offset = 0;
int count = 20;
WxMpMaterialFileBatchGetResult result;

do {
    result = wxService.getMaterialService()
        .materialFileBatchGet(WxConsts.MediaFileType.IMAGE, offset, count);
    allImages.addAll(result.getItems());
    offset += count;
} while (result.getItemCount() == count);

System.out.println("Retrieved " + allImages.size() + " images");

// Get all news articles
List<WxMpMaterialNewsBatchGetResult.WxMpMaterialNewsBatchGetNewsItem> allNews = new ArrayList<>();
offset = 0;
WxMpMaterialNewsBatchGetResult newsResult;

do {
    newsResult = wxService.getMaterialService().materialNewsBatchGet(offset, count);
    allNews.addAll(newsResult.getItems());
    offset += count;
} while (newsResult.getItemCount() == count);

System.out.println("Retrieved " + allNews.size() + " news articles");

File Size Limits

WeChat has specific file size limits for different media types:

  • Images: 10MB max, supports JPG, PNG formats
  • Voice: 2MB max, duration ≤ 60 seconds, supports AMR, MP3 formats
  • Video: 10MB max, duration ≤ 60 seconds, supports MP4 format
  • Thumb: 64KB max, supports JPG format

Temporary vs Permanent Materials

Temporary Materials

  • Valid for 3 days
  • Used for immediate message sending
  • Limited storage quota
  • Automatically cleaned up

Permanent Materials

  • No expiration time
  • Used for long-term storage
  • Higher storage quota
  • Must be manually deleted

Error Handling

try {
    WxMpMaterialUploadResult result = wxService.getMaterialService()
        .materialFileUpload(WxConsts.MediaFileType.IMAGE, imageFile);
} catch (WxErrorException e) {
    int errorCode = e.getError().getErrorCode();
    
    switch (errorCode) {
        case 40004:
            System.err.println("Invalid media type");
            break;
        case 40005:
            System.err.println("Invalid file type");
            break;
        case 40006:
            System.err.println("Invalid file size");
            break;
        case 40007:
            System.err.println("Invalid media file id");
            break;
        case 40008:
            System.err.println("Invalid message type");
            break;
        case 45001:
            System.err.println("Media size out of limit");
            break;
        case 45002:
            System.err.println("Message content out of limit");
            break;
        case 45003:
            System.err.println("Title length out of limit");
            break;
        case 45004:
            System.err.println("Description length out of limit");
            break;
        case 45005:
            System.err.println("URL length out of limit");
            break;
        case 45006:
            System.err.println("Picture URL length out of limit");
            break;
        default:
            System.err.println("Upload failed: " + e.getError().getErrorMsg());
    }
}

Best Practices

  1. File Management: Always close InputStreams and delete temporary files
  2. Error Handling: Implement retry logic for network failures
  3. Quota Management: Monitor material counts to avoid quota limits
  4. Naming Convention: Use descriptive names for materials
  5. Content Validation: Validate content before upload to avoid rejection
  6. Thumbnail Management: Always upload thumbnails for videos
  7. URL Validation: Ensure external URLs in articles are accessible

Install with Tessl CLI

npx tessl i tessl/maven-com-github-binarywang--weixin-java-mp

docs

advanced-services.md

index.md

material-management.md

menu-management.md

message-handling.md

service-management.md

shopping-guide.md

template-messaging.md

user-management.md

tile.json